package com.huilian.iotbox.admin.wap.service.impl;

import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONObject;
import com.alibaba.fastjson.parser.Feature;
import com.alibaba.fastjson.serializer.SerializerFeature;
import com.github.pagehelper.PageHelper;
import com.github.pagehelper.PageInfo;
import com.huilian.iotbox.admin.wap.dao.MerchantDao;
import com.huilian.iotbox.admin.wap.dao.QualificationDao;
import com.huilian.iotbox.admin.wap.service.*;
import com.huilian.iotbox.data.common.RedisKey;
import com.huilian.iotbox.data.common.ServerResponse;
import com.huilian.iotbox.data.config.AgencyConfig;
import com.huilian.iotbox.data.config.MiddlewareConfig;
import com.huilian.iotbox.data.dto.*;
import com.huilian.iotbox.data.enums.*;
import com.huilian.iotbox.data.exception.ControllerException;
import com.huilian.iotbox.data.po.Merchant;
import com.huilian.iotbox.data.po.MerchantPayCompany;
import com.huilian.iotbox.data.po.PayCompany;
import com.huilian.iotbox.data.po.Qualification;
import com.huilian.iotbox.data.properties.ConfigProperties;
import com.huilian.iotbox.data.properties.QiniuProperties;
import com.huilian.iotbox.data.service.BaiduApiService;
import com.huilian.iotbox.data.service.ErrorLogCommonService;
import com.huilian.iotbox.data.utils.HttpUtils;
import com.huilian.iotbox.data.utils.HttpsMain;
import com.huilian.iotbox.data.utils.RsaUtil;
import com.huilian.iotbox.data.vo.*;
import lombok.Getter;
import lombok.extern.slf4j.Slf4j;
import org.apache.http.HttpEntity;
import org.apache.http.entity.ContentType;
import org.apache.http.entity.mime.MultipartEntityBuilder;
import org.apache.http.entity.mime.content.StringBody;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.stereotype.Service;
import org.springframework.util.ObjectUtils;
import org.springframework.util.StringUtils;
import org.springframework.web.multipart.MultipartFile;

import javax.annotation.Resource;
import javax.imageio.ImageIO;
import javax.servlet.http.HttpServletRequest;
import java.awt.*;
import java.awt.image.BufferedImage;
import java.io.*;
import java.math.BigDecimal;
import java.net.HttpURLConnection;
import java.net.URL;
import java.security.KeyManagementException;
import java.security.NoSuchAlgorithmException;
import java.security.NoSuchProviderException;
import java.sql.Timestamp;
import java.text.SimpleDateFormat;
import java.util.*;
import java.util.List;
import java.util.concurrent.CompletableFuture;
import java.util.concurrent.ThreadPoolExecutor;
import java.util.concurrent.TimeUnit;

/**
 * @author 谢洛涛
 * @date 2021/3/22 9:49
 */
@Service
@Slf4j
public class MerchantServiceImpl implements MerchantService {
    /**
     * 商户默认费率
     **/
    private static BigDecimal feeValue = new BigDecimal("0.006");
    @Autowired
    private ThreadPoolExecutor executor;
    @Resource
    private MerchantDao merchantDao;
    @Autowired
    private UserService userService;
    @Autowired
    private AgencyConfig agencyConfig;
    @Autowired
    private RegionService regionService;
    @Autowired
    private ErrorLogCommonService errorLogCommonService;
    @Autowired
    private QiniuProperties qiniuProperties;
    @Autowired
    private BaiduApiService baiduApiService;
    @Autowired
    private ConfigProperties configProperties;
    @Autowired
    private PayCompanyService payCompanyService;
    @Autowired
    private BankRegionService bankRegionService;
    @Autowired
    private RabbitSenderService rabbitSenderService;
    @Autowired
    private QualificationService qualificationService;
    @Autowired
    private MerchantStoreService merchantStoreService;
    @Autowired
    private RedisTemplate<String, Serializable> redisTemplate;
    @Autowired
    private MerchantPayCompanyService merchantPayCompanyService;

    @Resource
    private QualificationDao qualificationDao;

    /**
     * 商户创建资质并且进件-H5端
     *
     * @param merchantDto
     * @param userInfo
     * @return
     * @throws Exception
     */
    @Override
    public ServerResponse merchantRegister(MerchantDto merchantDto, UserInfo userInfo) throws Exception {
        // 判断商户订单号是否存
        String outTrandeNo = null;
        if (StringUtils.isEmpty(merchantDto.getOutTradeNo())) {
            outTrandeNo = UUID.randomUUID().toString();
            PayCompany payCompany = payCompanyService.findDefaultPayCompany(1);
            merchantDto.setPayCompanyCode(payCompany.getCode());
            int random = (int) (Math.random() * 900 + 100);
            String email = String.valueOf(System.currentTimeMillis()) + random + "@qq.com";
            merchantDto.setEmail(email);
        } else {
            outTrandeNo = merchantDto.getOutTradeNo();
        }
        //组装进件参数
        MerchantBankCardDto merchantBankCard = new MerchantBankCardDto(
                merchantDto.getBankCardNo(),   //银行卡号
                merchantDto.getBankCertName(),  //账户名
                merchantDto.getAccountType(), //结算类型，01：对私 02：对公
                merchantDto.getContactLine(),//联行号
                merchantDto.getBankName(),//银行名称
                merchantDto.getBankProvince(),//开户行省
                merchantDto.getBankCity(),//开户行市
                PrincipalCertTypeEnum.IdentityCard.getCertCode(),
                merchantDto.getPrincipalCertNo(),//身份证号
                merchantDto.getBankRegion(),//持卡人地址
                merchantDto.getBankCardA(),//银行卡正面
                merchantDto.getBankCardB()//银行卡反面
        );
        List<MerchantFeeParamDto> feeParamList = new ArrayList<>();
        MerchantDetailDto merchantDetail = new MerchantDetailDto(
                merchantDto.getLegalPerson(),//企业法人名称 个体工商户不需要填写
                merchantDto.getBussAuthNum(),//营业执照号
                merchantDto.getPrincipalPerson(),//负责人名称或企业法人代表
                merchantDto.getContactMobile(),//负责人手机号
                PrincipalCertTypeEnum.IdentityCard.getCertCode(),
                merchantDto.getPrincipalCertNo(),//身份证号
                merchantDto.getProvince(),//商户所在省
                merchantDto.getCity(),//市
                merchantDto.getDistrict(),//区
                merchantDto.getAddress(),//商户所在详细地址
                merchantDto.getEmail(),//邮箱
                merchantDto.getServicePhoneNo(),//公司电话
                "",
                "",
                merchantDto.getCertPhotoA(),//身份证正面
                merchantDto.getCertPhotoB(), // 身份证反面
                merchantDto.getLicensePhoto(),
                merchantDto.getIndustryLicensePhoto(),
                merchantDto.getShopPhoto(), //门头照
                merchantDto.getShopEntrancePhoto(), //场地内景照
                "",
                merchantDto.getCheckStandPhoto(),
                merchantDto.getHandHoldIdCard()
        );
        //费率
        feeParamList.add(new MerchantFeeParamDto(PayChannelEnum.WX.getChnCode(), MerchantFeeTypeEnum.T1.getFeeCode(), feeValue));
        feeParamList.add(new MerchantFeeParamDto(PayChannelEnum.Ali.getChnCode(), MerchantFeeTypeEnum.T1.getFeeCode(), feeValue));
        //outTradeNo 必须每次都一样 如果不一样那么提交过来就是修改或者报错
        // 修改的话需要满足 条件 商户状态是 平台审核以及等待提交这个状态才会修改
        merchantDto.setOutTradeNo(outTrandeNo);
        if (MerchantTypeEnum.Natural.getCode().equals(merchantDto.getMerchantType())) {
            merchantDto.setMerchantName("商户_" + merchantDto.getPrincipalPerson());
        } else {
            merchantDto.setMerchantName(merchantDto.getLegalPerson());
        }
        merchantDto.setMccCode(MccEnum.Entertainment.getMccCode());
        merchantDto.setDealType(DealTypeEnum.EntityAndInternet.getDealCode());
        merchantDto.setStlTyp("1");
        int i = (int) (Math.random() * 900) + 100;
        String username = merchantDto.getContactMobile() + "/" + i;
        merchantDto.setUsername(username);
        merchantDto.setPath(configProperties.getClientBackEndUrl() + "/");
        JSONObject jsonObject = JSONObject.parseObject(JSON.toJSONString(merchantDto), Feature.OrderedField);
        jsonObject.put("merchantDetail", merchantDetail);
        jsonObject.put("merchantBankCard", merchantBankCard);
        jsonObject.put("merchantFeeList", feeParamList);

        String param = HttpUtils.format(agencyConfig, jsonObject, FunctionEnum.MERCHANT_REGISTER, merchantDto.getPayCompanyCode());
        log.info("请求报文: {}", param);
        String response = HttpsMain.httpsReq(MiddlewareConfig.MerchantRegists, param);
        log.info("响应报文: {}", response);
        final Map<String, Object> result = HttpUtils.getResultData(response);
        log.info("响应报文result: {}", result);
        if (RequestStatus.SUCCESS.getCode().equals(result.get("status")) && RequestStatus.SUCCESS_CODE.getCode().equals(result.get("code"))) {
            Map<String, String> resMap = (Map<String, String>) result.get("data");
            Merchant merchant = new Merchant();
            merchant.setOutTradeNo(outTrandeNo);
            MerchantVo merchantVo = merchantDao.findMerchantByOutTradeNo(merchant);
            if (StringUtils.isEmpty(merchantVo)) {
                // 添加资质编号
                Qualification qualification = new Qualification();
                qualification.setCertNo(resMap.get("certNo"));
                qualification.setUserId(userInfo.getId());
                qualification.setType(QualificationTypeEnum.MAIN_QUALIFICATIONS.getCode());
                if (MerchantTypeEnum.Natural.getCode().equals(merchantDto.getMerchantType())) {
                    qualification.setName(merchantDto.getPrincipalPerson());
                } else {
                    qualification.setName(merchantDto.getLegalPerson());
                }
                qualificationService.addQualification(qualification);
//                添加商户
                merchant.setQualificationId(qualification.getId());
                merchant.setMerchantId(resMap.get("hlMerchantId"));
                merchant.setFeeValue(feeValue);
                merchant.setPayCompanyCode(merchantDto.getPayCompanyCode());
                merchant.setStatus(MerchantStatusEnum.AUDITING_YIHAO.getCode());
                merchant.setMerchantShortName(merchantDto.getMerchantShortName());
                merchantDao.addMerchant(merchant);
                MerchantPayCompany merchantPayCompany = new MerchantPayCompany();
                merchantPayCompany.setMchId(merchant.getId());
                merchantPayCompany.setPayCompanyCode(merchantDto.getPayCompanyCode());
                merchantPayCompany.setBankCardNo(merchantBankCard.getBankCardNo());
                merchantPayCompany.setBankCertName(merchantBankCard.getBankCertName());
                merchantPayCompanyService.addMerchantPayCompany(merchantPayCompany);
            } else {
                merchantDao.updateMerchant(merchant);
                MerchantPayCompanyDto merchantPayCompanyDto = new MerchantPayCompanyDto();
                merchantPayCompanyDto.setMchId(merchantVo.getId());
                merchantPayCompanyDto.setPayCompanyCode(merchantDto.getPayCompanyCode());
                merchantPayCompanyDto.setBankCardNo(merchantBankCard.getBankCardNo());
                merchantPayCompanyDto.setBankCertName(merchantBankCard.getBankCertName());
                merchantPayCompanyService.update(merchantPayCompanyDto);
            }
            UserDto userDto = new UserDto();
            userDto.setId(userInfo.getId());
            userDto.setReceiptType(MchTypeEnum.OWN.getCode());
            userService.updateUserReceiptType(userDto);
            return ServerResponse.createBySuccess(merchant);
        } else {
            return ServerResponse.createByErrorMessage((String) result.get("msg"));
        }
    }

    /**
     * 上传进件图片
     */
    @Override
    public ServerResponse uploadphoto(MultipartFile image, String type) throws IOException {
        Map<String, Object> bizmap = new HashMap<String, Object>();

        bizmap.put("outTradeNo", UUID.randomUUID().toString());
        String bizcontent = JSON.toJSONString(bizmap);
        Map<String, String> map = new TreeMap<>();
        System.out.println("业务参数JSON格式字符串:" + bizcontent);
        map.put("content", bizcontent);
        map.put("function", FunctionEnum.MERCHANT_UPLOADPHOTO.getCode());
        map.put("timestamp", new Timestamp(System.currentTimeMillis()).toString());// 请求时间戳,时区为GMT+8(北京时间)
        //系统参数
        map.put("agencyNo", agencyConfig.getIsvOrgId());// 授权用户名(固定值)
        String signStr = JSON.toJSONString(map, SerializerFeature.SortField);
        String sign = RsaUtil.sign(signStr, agencyConfig.getPrivateKey());
        map.put("sign", sign);

        MultipartEntityBuilder entityBuilder = MultipartEntityBuilder.create();
        entityBuilder.addBinaryBody("picture", image.getInputStream(), ContentType.DEFAULT_BINARY, image.getName()).build();
        for (Map.Entry<String, String> entry : map.entrySet()) {
            entityBuilder.addPart(entry.getKey(), new StringBody(entry.getValue()));
        }

        HttpEntity reqEntity = entityBuilder.build();
        String response = HttpsMain.httpPost(MiddlewareConfig.uploadUrl, reqEntity);
        log.info("响应报文: {}", response);
        final Map<String, Object> result = HttpUtils.getResultData(response);
        log.info("响应报文result: {}", result);
        if (RequestStatus.SUCCESS.getCode().equals(result.get("status")) && RequestStatus.SUCCESS_CODE.getCode().equals(result.get("code"))) {
            Map<String, String> resMap = (Map<String, String>) result.get("data");
            return ServerResponse.createBySuccess(resMap.get("photoUrl"));
        } else {
            return ServerResponse.createByErrorMessage((String) result.get("msg"));
        }
    }

    /**
     * 进件回调
     *
     * @param request
     * @throws Exception
     */
    @Override
    public void merchantRegisterNotice(HttpServletRequest request) throws Exception {
        BufferedReader reader = new BufferedReader(new InputStreamReader(request.getInputStream()));
        String tempLine = "";
        StringBuffer resultBuffer = new StringBuffer();
        while ((tempLine = reader.readLine()) != null) {
            resultBuffer.append(tempLine).append(System.getProperty("line.separator"));
        }
        String res = resultBuffer.toString();
        final Map<String, Object> result = HttpUtils.getResultData(res);
        log.info("进件回调响应报文: {}", result);
        log.info("status: {}", result.get("status"));
        log.info("code: {}", result.get("code"));
        if (RequestStatus.SUCCESS.getCode().equals(result.get("status")) && RequestStatus.SUCCESS_CODE.getCode().equals(result.get("code"))) {
            Map<String, Object> resMap = (Map<String, Object>) result.get("data");
            MerchantDto merchantDto = new MerchantDto();
            merchantDto.setOutTradeNo((String) resMap.get("outTradeNo"));
            merchantDto.setPayCompanyCode((String) resMap.get("payCompanyCode"));
            log.info("merchantDto: {}", JSON.toJSONString(merchantDto));
            MerchantVo merchantVo = merchantDao.findMerchantByOutTradeNoAndPayCompanyCode(merchantDto);
            log.info("merchantVo: {}", JSON.toJSONString(merchantVo));
            if (!StringUtils.isEmpty(merchantVo) && !MerchantStatusEnum.SUCCESS.getCode().equals(merchantVo.getStatus())) {
                Merchant merchant = new Merchant();
                merchant.setMerchantId((String) resMap.get("hlMerchantId"));
                merchant.setOutTradeNo((String) resMap.get("outTradeNo"));
                merchant.setFailReason((String) resMap.get("failReason"));
                merchant.setStatus((Integer) resMap.get("registerStatus"));
                merchantDao.updateMerchant(merchant);
                if (MerchantStatusEnum.SUCCESS.getCode().equals(merchant.getStatus())) {
                    final Merchant merchantByMerchantId = merchantDao.findMerchantByMerchantId(merchant.getMerchantId());
                    MerchantStoreDto merchantStoreDto = new MerchantStoreDto();
                    merchantStoreDto.setUserId(merchantVo.getUserId());
                    merchantStoreDto.setMchId(merchantVo.getId());
                    if (!StringUtils.isEmpty(merchantByMerchantId)) {
                        merchantStoreDto.setTiktokRate(merchantByMerchantId.getFeeValue());
                        merchantStoreDto.setMeiTuanRate(merchantByMerchantId.getFeeValue());
                    }
                    merchantStoreService.updateMerchantStore(merchantStoreDto);
                }
            }
        }


        /**
         * {
         *   "code": "0000",
         *   "data": {
         *     "failReason": "风险商户",
         *     "outTradeNo": "6bd19501-2572-4761-88a8-bd7718e68585",
         *     "payCompanyCode": "yeahka",
         *     "registerStatus": 2
         *   },
         *   "status": "S",
         *   "timestamp": "1663407836225"
         * }
         */

    }

    @Override
    public ServerResponse findMerchant(Integer type, UserInfo userInfo) {
        MerchantDto merchantDto = new MerchantDto();
        merchantDto.setUserId(userInfo.getId());
        merchantDto.setType(type);
        return ServerResponse.createBySuccess(merchantDao.findMerchant(merchantDto));
    }

    /**
     * 查询商户详情-公众号
     *
     * @param merchant
     * @return
     * @throws Exception
     */
    @Override
    public ServerResponse findMerchantInfo(Merchant merchant) throws Exception {
        Map<String, Object> form = new HashMap<>();
        form.put("outTradeNo", merchant.getOutTradeNo());
        form.put("HlMerchantId", merchant.getMerchantId());
//        log.info(agencyConfig.getPrivateKey());
        String param = HttpUtils.format(agencyConfig, form, FunctionEnum.MERCHANT_QUERY, merchant.getPayCompanyCode());
        String response = HttpsMain.httpsReq(MiddlewareConfig.merchantInfo, param);
        final Map<String, Object> result = HttpUtils.getResultData(response);
        log.info("响应报文result: {}", result);
        if (RequestStatus.SUCCESS.getCode().equals(result.get("status")) && RequestStatus.SUCCESS_CODE.getCode().equals(result.get("code"))) {
//            JSONArray settleRecordsrt =  result.get("data");
            Map<String, Object> resMap = (Map<String, Object>) result.get("data");
            Map<String, Object> res = (Map<String, Object>) resMap.get("merchant");
            Map<String, String> merchantBankCard = (Map<String, String>) res.get("merchantBankCard");
            Map<String, String> merchantDetail = (Map<String, String>) res.get("merchantDetail");
            Map<String, String> hlMerchant = (Map<String, String>) res.get("hlMerchant");
            MerchantVo merchantVo = new MerchantVo();
            merchantVo.setOutTradeNo((String) res.get("outTradeNo"));
            merchantVo.setStatus((Integer) res.get("status"));
            merchantVo.setPayCompanyCode((String) res.get("payCompanyCode"));
            merchantVo.setFailReason((String) res.get("failReason"));
            merchantVo.setWechatMerchId((String) res.get("wechatMerchId"));
            merchantVo.setMerchantId(hlMerchant.get("hlMerchantId"));
            merchantVo.setMerchantName("商户_" + merchantDetail.get("principalPerson"));
            // 结算卡信息
            merchantVo.setAccountType(merchantBankCard.get("accountType"));
            merchantVo.setBankCardA(merchantBankCard.get("bankCardA"));
            merchantVo.setBankCardB(merchantBankCard.get("bankCardB"));
            merchantVo.setBankCardNo(merchantBankCard.get("bankCardNo"));
            merchantVo.setBankCertName(merchantBankCard.get("bankCertName"));
            merchantVo.setContactLine(merchantBankCard.get("contactLine"));
            merchantVo.setBankProvince(merchantBankCard.get("branchProvince"));
            merchantVo.setBankCity(merchantBankCard.get("branchCity"));
            merchantVo.setBankName(merchantBankCard.get("bankName"));
            // 商户个人信息
            merchantVo.setMerchantType((String) res.get("merchantType"));
            merchantVo.setCertPhotoA(merchantDetail.get("certPhotoA"));
            merchantVo.setCertPhotoB(merchantDetail.get("certPhotoB"));
            merchantVo.setPrincipalCertNo(merchantDetail.get("principalCertNo"));
            merchantVo.setPrincipalPerson(merchantDetail.get("principalPerson"));
            merchantVo.setContactMobile(merchantDetail.get("principalMobile"));
            merchantVo.setServicePhoneNo(merchantDetail.get("servicePhoneNo"));
            merchantVo.setLicensePhoto(merchantDetail.get("licensePhoto"));
            merchantVo.setIndustryLicensePhoto(merchantDetail.get("industryLicensePhoto"));
            merchantVo.setLegalPerson(merchantDetail.get("legalPerson"));
            merchantVo.setBussAuthNum(merchantDetail.get("bussAuthNum"));
            merchantVo.setProvince(merchantDetail.get("province"));
            merchantVo.setCity(merchantDetail.get("city"));
            merchantVo.setDistrict(merchantDetail.get("district"));
            merchantVo.setAddress(merchantDetail.get("address"));
            merchantVo.setEmail(merchantDetail.get("email"));
            merchantVo.setMerchantShortName(merchantDetail.get("alias"));
            // 场地图片
            merchantVo.setShopPhoto(merchantDetail.get("shopPhoto"));
            merchantVo.setShopEntrancePhoto(merchantDetail.get("shopEntrancePhoto"));
            merchantVo.setCheckStandPhoto(merchantDetail.get("checkStandPhoto"));
            merchantVo.setHandHoldIdCard(merchantDetail.get("handHoldIdCard"));

            String region = regionService.findRegion(merchantVo.getProvince(), merchantVo.getCity(), merchantVo.getDistrict());
            String bankRegion = bankRegionService.findBankRegion(merchantVo.getBankProvince(), merchantVo.getBankCity());
            merchantVo.setBankRegion(bankRegion);
            merchantVo.setRegion(region);
            return ServerResponse.createBySuccess(merchantVo);
        } else {
            return ServerResponse.createBySuccess();
        }
    }

    @Override
    public PageInfo findMerchantSubAccountByUserId(MerchantDto merchantDto) throws IOException, NoSuchAlgorithmException, NoSuchProviderException, KeyManagementException {
        merchantDto.setQualificationType(QualificationTypeEnum.COOPERATION_QUALIFICATION.getCode());
        PageHelper.startPage(merchantDto.getPageNum(), merchantDto.getPageSize());
        List<MerchantVo> list = merchantDao.findMerchantSubAccountByUserId(merchantDto);
        Map<String, Object> form = new HashMap<>();
        for (MerchantVo merchantVo : list) {
            if (merchantVo.getStatus().equals(MerchantStatusEnum.OFF.getCode()) || merchantVo.getStatus().equals(MerchantStatusEnum.SUCCESS.getCode()) || merchantVo.getStatus().equals(MerchantStatusEnum.RISK.getCode())) {
                form.put("outTradeNo", merchantVo.getOutTradeNo());
                form.put("HlMerchantId", merchantVo.getMerchantId());
                String param = HttpUtils.format(agencyConfig, form, FunctionEnum.MERCHANT_QUERY, merchantVo.getPayCompanyCode());
                String response = HttpsMain.httpsReq(MiddlewareConfig.merchantInfo, param);
                final Map<String, Object> result = HttpUtils.getResultData(response);
                log.info("响应报文result: {}", result);
                if (RequestStatus.SUCCESS.getCode().equals(result.get("status")) && RequestStatus.SUCCESS_CODE.getCode().equals(result.get("code"))) {
                    Map<String, Object> resMap = (Map<String, Object>) result.get("data");
                    Map<String, Object> res = (Map<String, Object>) resMap.get("merchant");
                    merchantVo.setWechatMerchId((String) res.get("wechatMerchId"));
                    merchantVo.setAliMerchId((String) res.get("smid"));
                }
            }
        }
        return new PageInfo(list);
    }

    @Override
    public PageInfo findMerchantListByUserId(MerchantDto merchantDto) throws IOException, NoSuchAlgorithmException, NoSuchProviderException, KeyManagementException {
        PageHelper.startPage(merchantDto.getPageNum(), merchantDto.getPageSize());
        List<MerchantVo> list = merchantDao.findMerchantListByUserId(merchantDto);
        Map<String, Object> form = new HashMap<>();
        for (MerchantVo merchantVo : list) {
            if (merchantVo.getStatus().equals(MerchantStatusEnum.OFF.getCode()) || merchantVo.getStatus().equals(MerchantStatusEnum.SUCCESS.getCode()) || merchantVo.getStatus().equals(MerchantStatusEnum.RISK.getCode())) {
                form.put("outTradeNo", merchantVo.getOutTradeNo());
                form.put("HlMerchantId", merchantVo.getMerchantId());
                String param = HttpUtils.format(agencyConfig, form, FunctionEnum.MERCHANT_QUERY, merchantVo.getPayCompanyCode());
                String response = HttpsMain.httpsReq(MiddlewareConfig.merchantInfo, param);
                final Map<String, Object> result = HttpUtils.getResultData(response);
                log.info("响应报文result: {}", result);
                if (RequestStatus.SUCCESS.getCode().equals(result.get("status")) && RequestStatus.SUCCESS_CODE.getCode().equals(result.get("code"))) {
                    Map<String, Object> resMap = (Map<String, Object>) result.get("data");
                    Map<String, Object> res = (Map<String, Object>) resMap.get("merchant");
                    merchantVo.setWechatMerchId((String) res.get("wechatMerchId"));
                    merchantVo.setAliMerchId((String) res.get("smid"));
                }
            }
        }
        PageInfo pagResult = new PageInfo(list);
        return pagResult;
    }

    /**
     * 查询商户详情-小程序
     *
     * @param merchant
     * @return
     * @throws Exception
     */
    @Override
    public ServerResponse findMerchantInfoByApplet(Merchant merchant) throws Exception {
        Map<String, Object> form = new HashMap<>();
        form.put("outTradeNo", merchant.getOutTradeNo());
        form.put("HlMerchantId", merchant.getMerchantId());

//        log.info(agencyConfig.getPrivateKey());
        String param = HttpUtils.format(agencyConfig, form, FunctionEnum.MERCHANT_QUERY, merchant.getPayCompanyCode());
        String response = HttpsMain.httpsReq(MiddlewareConfig.merchantInfo, param);
        final Map<String, Object> result = HttpUtils.getResultData(response);

        log.info("响应报文result: {}", result);
        if (RequestStatus.SUCCESS.getCode().equals(result.get("status")) && RequestStatus.SUCCESS_CODE.getCode().equals(result.get("code"))) {
            Map<String, Object> resMap = (Map<String, Object>) result.get("data");
            Map<String, Object> res = (Map<String, Object>) resMap.get("merchant");
            Map<String, String> merchantBankCard = (Map<String, String>) res.get("merchantBankCard");
            Map<String, String> merchantDetail = (Map<String, String>) res.get("merchantDetail");
            Map<String, String> hlMerchant = (Map<String, String>) res.get("hlMerchant");

            MerchantVo merchantVo = new MerchantVo();
            merchantVo.setOutTradeNo((String) res.get("outTradeNo"));
            merchantVo.setStatus((Integer) res.get("status"));
            merchantVo.setPayCompanyCode((String) res.get("payCompanyCode"));
            merchantVo.setFailReason((String) res.get("failReason"));
            merchantVo.setWechatMerchId((String) res.get("wechatMerchId"));
            merchantVo.setAliMerchId((String) res.get("smid"));
            merchantVo.setCanalMerchantId((String) res.get("merchantId"));
            merchantVo.setMerchantId(hlMerchant.get("hlMerchantId"));
            merchantVo.setMerchantName("商户_" + merchantDetail.get("principalPerson"));
            // 结算卡信息
            merchantVo.setAccountType(merchantBankCard.get("accountType"));
            merchantVo.setBankCardA(merchantBankCard.get("bankCardA"));
            merchantVo.setBankCardB(merchantBankCard.get("bankCardB"));
            merchantVo.setBankCardNo(merchantBankCard.get("bankCardNo"));
            merchantVo.setBankCertName(merchantBankCard.get("bankCertName"));
            merchantVo.setContactLine(merchantBankCard.get("contactLine"));
            merchantVo.setBankProvince(merchantBankCard.get("branchProvince"));
            merchantVo.setBankCity(merchantBankCard.get("branchCity"));
            merchantVo.setBankName(merchantBankCard.get("bankName"));
            // 商户个人信息
            merchantVo.setMerchantType((String) res.get("merchantType"));
            merchantVo.setCertPhotoA(merchantDetail.get("certPhotoA"));
            merchantVo.setCertPhotoB(merchantDetail.get("certPhotoB"));
            merchantVo.setPrincipalCertNo(merchantDetail.get("principalCertNo"));
            merchantVo.setPrincipalPerson(merchantDetail.get("principalPerson"));
            merchantVo.setContactMobile(merchantDetail.get("principalMobile"));
            merchantVo.setServicePhoneNo(merchantDetail.get("servicePhoneNo"));
            merchantVo.setLicensePhoto(merchantDetail.get("licensePhoto"));
            merchantVo.setIndustryLicensePhoto(merchantDetail.get("industryLicensePhoto"));
            merchantVo.setLegalPerson(merchantDetail.get("legalPerson"));
            merchantVo.setBussAuthNum(merchantDetail.get("bussAuthNum"));
            merchantVo.setProvince(merchantDetail.get("province"));
            merchantVo.setCity(merchantDetail.get("city"));
            merchantVo.setDistrict(merchantDetail.get("district"));
            merchantVo.setAddress(merchantDetail.get("address"));
            merchantVo.setEmail(merchantDetail.get("email"));
            merchantVo.setMerchantShortName(merchantDetail.get("alias"));
            merchantVo.setProvinceCode(merchantDetail.get("province"));
            merchantVo.setCityCode(merchantDetail.get("city"));
            merchantVo.setDistrictCode(merchantDetail.get("district"));
            // 场地图片
            merchantVo.setShopPhoto(merchantDetail.get("shopPhoto"));
            merchantVo.setShopEntrancePhoto(merchantDetail.get("shopEntrancePhoto"));
            merchantVo.setCheckStandPhoto(merchantDetail.get("checkStandPhoto"));
            merchantVo.setHandHoldIdCard(merchantDetail.get("handHoldIdCard"));
            // 支付宝微信认证信息
            Map<String, Object> form2 = new HashMap<>();
            form2.put("HlMerchantId", merchant.getMerchantId());
            String paramValue = HttpUtils.format(agencyConfig, form2, FunctionEnum.MERCHANT_REGISTER_QUERY, merchant.getPayCompanyCode());
            log.info("商户注册查询接口请求报文{}", paramValue);
            String responseValue = HttpsMain.httpsReq(MiddlewareConfig.Merchant + "/queryAuthorizeInfo", paramValue);
            log.info("商户注册查询接口响应报文{}", responseValue);
            if (!RsaUtil.verifyResponseSign(responseValue)) {
                log.info("验签失败");
                throw new ControllerException("验签失败");
            }
            JSONObject jsonObject = JSONObject.parseObject(responseValue);
            Map<String, Object> data = (Map<String, Object>) jsonObject.get("data");
            Map<String, Object> merchantData = (Map<String, Object>) data.get("merchant");
            Integer status = (Integer) merchantData.get("status");

            merchantVo.setAuthenticationStatus(status);
            if (status == 1) {
                String smId = (String) merchantData.get("smid");
                String wechatMerchId = (String) merchantData.get("wechatMerchId");
                String aliQrcode = (String) merchantData.get("aliQrcode");
                String qrcodeData = (String) merchantData.get("qrcodeData");
                merchantVo.setAliApplymentState((String) merchantData.get("aliApplymentState"));
                merchantVo.setApplymentState((String) merchantData.get("applymentState"));
                if (smId != null) {
                    merchantVo.setAliQrcode(aliQrcode);
                }
                if (wechatMerchId != null) {
                    merchantVo.setQrcodeData(qrcodeData);
                }
            }
            //同步状态值
            Merchant editMerchant = new Merchant();
            editMerchant.setWeChatApplymentState((String) merchantData.get("applymentState"));
            editMerchant.setWeChatAuthorizeState((String) merchantData.get("authorizeState"));
            editMerchant.setAliApplymentState((String) merchantData.get("aliApplymentState"));
            editMerchant.setAliAuthorizeState((String) merchantData.get("aliAuthorizeState"));
            editMerchant.setOutTradeNo(merchantVo.getOutTradeNo());
            merchantDao.updateMerchant(editMerchant);

            String region = regionService.findRegion(merchantVo.getProvince(), merchantVo.getCity(), merchantVo.getDistrict());
            String bankRegion = bankRegionService.findBankRegion(merchantVo.getBankProvince(), merchantVo.getBankCity());
            merchantVo.setBankRegion(bankRegion);
            merchantVo.setRegion(region);
            return ServerResponse.createBySuccess(merchantVo);
        } else {
            return ServerResponse.createBySuccess();
        }
    }

    /**
     * 开通乐刷分帐获取短信接口-小程序
     *
     * @param merchantDto
     * @return
     */
    @Override
    public ServerResponse sendCodeByApplet(MerchantDto merchantDto) throws IOException, NoSuchAlgorithmException, NoSuchProviderException, KeyManagementException {

        if (StringUtils.isEmpty(merchantDto.getMerchantId())) {
            return ServerResponse.createByErrorMessage("商户ID不能为空");
        }
        if (StringUtils.isEmpty(merchantDto.getAuthTypes())) {
            return ServerResponse.createByErrorMessage("标识不能为空");
        }
        if (StringUtils.isEmpty(merchantDto.getPayCompanyCode())) {
            return ServerResponse.createByErrorMessage("支付渠道号不能为空");
        }


        Map<String, Object> form = new HashMap<>();
        if (merchantDto.getAuthTypes().compareTo(1) == 0) {
            if (StringUtils.isEmpty(merchantDto.getPhone())) {
                return ServerResponse.createByErrorMessage("手机号码不能为空");
            }
            form.put("phone", merchantDto.getPhone());
        } else if (merchantDto.getAuthTypes().compareTo(2) == 0) {
            if (StringUtils.isEmpty(merchantDto.getBankCardNo())) {
                return ServerResponse.createByErrorMessage("银行卡号不能为空");
            }
            form.put("bankCardNo", merchantDto.getBankCardNo());
        } else {
            return ServerResponse.createByErrorMessage("标识有误");
        }

        form.put("hlMerchantId", merchantDto.getMerchantId());
        form.put("authTypes", merchantDto.getAuthTypes());
        String param = HttpUtils.format(agencyConfig, form, FunctionEnum.MERCHANT_GAIN_OPEN_SPLIT_SENDCODE, merchantDto.getPayCompanyCode());
        String response = HttpsMain.httpsReq(MiddlewareConfig.Merchant, param);
        log.info("请求响应结果{}", response);
        //延签并返回map值
        final Map<String, Object> result = HttpUtils.getResultData(response);
        final String status = (String) result.get("status");
        final String code = (String) result.get("code");
        if (status.equals(RequestStatus.SUCCESS.getCode()) && code.equals(RequestStatus.SUCCESS_CODE.getCode())) {
            return ServerResponse.createBySuccess((String) result.get("msg"));
        } else {
            return ServerResponse.createByErrorMessage((String) result.get("msg"));
        }

    }

    /**
     * 开通乐刷分帐-小程序
     *
     * @param merchantDto
     * @return
     */
    @Override
    public ServerResponse codeVerifyByApplet(MerchantDto merchantDto) throws IOException, NoSuchAlgorithmException, NoSuchProviderException, KeyManagementException {

        if (StringUtils.isEmpty(merchantDto.getMerchantId())) {
            return ServerResponse.createByErrorMessage("商户ID不能为空");
        }
        if (StringUtils.isEmpty(merchantDto.getAuthTypes())) {
            return ServerResponse.createByErrorMessage("标识不能为空");
        }
        if (StringUtils.isEmpty(merchantDto.getPayCompanyCode())) {
            return ServerResponse.createByErrorMessage("支付渠道号不能为空");
        }

        Map<String, Object> form = new HashMap<>();
        if (merchantDto.getAuthTypes().compareTo(1) == 0) {
            if (StringUtils.isEmpty(merchantDto.getPhone())) {
                return ServerResponse.createByErrorMessage("手机号码不能为空");
            }
            form.put("phone", merchantDto.getPhone());
            form.put("smsCode", merchantDto.getData());
        } else if (merchantDto.getAuthTypes().compareTo(2) == 0) {
            if (StringUtils.isEmpty(merchantDto.getBankCardNo())) {
                return ServerResponse.createByErrorMessage("银行卡号不能为空");
            }
            form.put("bankCardNo", merchantDto.getBankCardNo());
            form.put("money", merchantDto.getData());
        } else {
            return ServerResponse.createByErrorMessage("标识有误");
        }

        form.put("hlMerchantId", merchantDto.getMerchantId());
        form.put("authTypes", merchantDto.getAuthTypes());
        form.put("phone", merchantDto.getPhone());
        form.put("bankCardNo", merchantDto.getBankCardNo());
        String param = HttpUtils.format(agencyConfig, form, FunctionEnum.MERCHANT_OPEN_SPLIT_VERIFY, merchantDto.getPayCompanyCode());
        String response = HttpsMain.httpsReq(MiddlewareConfig.Merchant, param);
        log.info("请求响应结果{}", response);
        //延签并返回map值
        final Map<String, Object> result = HttpUtils.getResultData(response);
        final String status = (String) result.get("status");
        final String code = (String) result.get("code");
        if (status.equals(RequestStatus.SUCCESS.getCode()) && code.equals(RequestStatus.SUCCESS_CODE.getCode())) {
            Merchant merchant = merchantDao.findMerchantByMerchantId(merchantDto.getMerchantId());
            MerchantPayCompanyDto merchantPayCompanyDto = new MerchantPayCompanyDto();
            merchantPayCompanyDto.setMchId(merchant.getId());
            merchantPayCompanyDto.setPayCompanyCode(merchantDto.getPayCompanyCode());
            merchantPayCompanyDto.setOpenSplitStatus(1);
            merchantPayCompanyService.update(merchantPayCompanyDto);
            return ServerResponse.createBySuccess((String) result.get("msg"));
        } else {
            return ServerResponse.createByErrorMessage((String) result.get("msg"));
        }
    }


    /**
     * 分账商户进件-微信小程序端
     *
     * @param merchantDto
     * @return
     * @throws Exception
     */
    @Override
    public ServerResponse subLedgerMerchantRegisterByApplet(MerchantDto merchantDto, UserInfo userInfo) throws Exception {
        log.info("merchantDto");
        log.info(JSON.toJSONString(merchantDto));
        ServerResponse serverResponse = this.checkParamSub(merchantDto);
        if (!serverResponse.getIsSuccess()) {
            return serverResponse;
        }
        // 判断商户订单号是否存
        String outTradeNo;
        if (StringUtils.isEmpty(merchantDto.getOutTradeNo())) {
            outTradeNo = UUID.randomUUID().toString();
            PayCompany payCompany = payCompanyService.findDefaultPayCompany(1);
            merchantDto.setPayCompanyCode(payCompany.getCode());
            int random = (int) (Math.random() * 900 + 100);
            String email = String.valueOf(System.currentTimeMillis()) + random + "@qq.com";
            merchantDto.setEmail(email);
        } else {
            outTradeNo = merchantDto.getOutTradeNo();
        }
        merchantDto.setOutTradeNo(outTradeNo);

        // 查询主商户相关信息
        Qualification q = new Qualification();
        q.setUserId(userInfo.getId());
        q.setType(QualificationTypeEnum.MAIN_QUALIFICATIONS.getCode());
        List<QualificationVo> qualificationByType = qualificationDao.findQualificationByType(q);
        if (qualificationByType.size() == 0) {
            return ServerResponse.createByErrorMessage("没有主商户");
        }
        Merchant m = new Merchant();
        for (QualificationVo qv : qualificationByType) {
            if ("helipay".equals(qv.getPayCompanyCode())) {
                m.setMerchantId(qv.getMerchantNo());
                m.setPayCompanyCode(qv.getPayCompanyCode());
                m.setOutTradeNo(qv.getOutTradeNo());
                break;
            }
        }

        ServerResponse merchantInfoByApplet = this.findMerchantInfoByApplet(m);
        MerchantVo mv = (MerchantVo) merchantInfoByApplet.getData();
        log.info("分账商户进件-微信小程序端-主商户信息: {}", JSON.toJSONString(mv));
        if (StringUtils.isEmpty(mv)) {
            return ServerResponse.createByErrorMessage("没有主商户详情信息");
        }
        //商户简称
        merchantDto.setMerchantShortName(mv.getMerchantShortName());
        //组装进件参数
        MerchantBankCardDto merchantBankCard = new MerchantBankCardDto(
                merchantDto.getBankCardNo(),   //银行卡号
                merchantDto.getBankCertName(),  //账户名
                merchantDto.getAccountType(), //结算类型，01：对私 02：对公
                merchantDto.getContactLine(),//联行号
                merchantDto.getBankName(),//银行名称
                merchantDto.getBankProvince(),//开户行省
                merchantDto.getBankCity(),//开户行市
                PrincipalCertTypeEnum.IdentityCard.getCertCode(),
                merchantDto.getPrincipalCertNo(),//身份证号
                merchantDto.getBankRegion(),//持卡人地址
                merchantDto.getBankCardA(),//银行卡正面
                merchantDto.getBankCardB()//银行卡反面
        );
        MerchantDetailDto merchantDetail = new MerchantDetailDto(
                merchantDto.getLegalPerson(),//企业法人名称 个体工商户不需要填写
                merchantDto.getBussAuthNum(),//营业执照号
                merchantDto.getPrincipalPerson(),//负责人名称或企业法人代表
                merchantDto.getContactMobile(),//负责人手机号
                PrincipalCertTypeEnum.IdentityCard.getCertCode(),
                merchantDto.getPrincipalCertNo(),//身份证号
                mv.getProvinceCode(),//商户所在省
                mv.getCityCode(),//市
                mv.getDistrictCode(),//区
                mv.getAddress(),//商户所在详细地址
                merchantDto.getEmail(),//邮箱
                merchantDto.getServicePhoneNo(),//公司电话
                "",
                "",
                merchantDto.getCertPhotoA(),//身份证正面
                merchantDto.getCertPhotoB(), // 身份证反面
                merchantDto.getLicensePhoto(),
                merchantDto.getIndustryLicensePhoto(),
                mv.getShopPhoto(), //门头照
                mv.getShopEntrancePhoto(), //场地内景照
                "",
                mv.getCheckStandPhoto(),//收银台照片
                merchantDto.getHandHoldIdCard()
        );
        if (MerchantTypeEnum.Natural.getCode().equals(merchantDto.getMerchantType())) {
            merchantDto.setMerchantName("商户_" + merchantDto.getPrincipalPerson());
        } else {
            merchantDto.setMerchantName(merchantDto.getLegalPerson());
        }
        merchantDto.setMccCode(MccEnum.Entertainment.getMccCode());
        merchantDto.setDealType(DealTypeEnum.EntityAndInternet.getDealCode());
        merchantDto.setStlTyp("1");
        int i = (int) (Math.random() * 900) + 100;
        String username = merchantDto.getContactMobile() + "/" + i;
        merchantDto.setUsername(username);
        merchantDto.setPath(configProperties.getClientBackEndUrl() + "/");
        List<MerchantFeeParamDto> feeParamList = new ArrayList<>();
        //费率
        feeParamList.add(new MerchantFeeParamDto(PayChannelEnum.WX.getChnCode(), MerchantFeeTypeEnum.T1.getFeeCode(), feeValue));
        feeParamList.add(new MerchantFeeParamDto(PayChannelEnum.Ali.getChnCode(), MerchantFeeTypeEnum.T1.getFeeCode(), feeValue));
        JSONObject jsonObject = JSONObject.parseObject(JSON.toJSONString(merchantDto), Feature.OrderedField);
        jsonObject.put("merchantDetail", merchantDetail);
        jsonObject.put("merchantBankCard", merchantBankCard);
        jsonObject.put("merchantFeeList", feeParamList);
        log.info("分账商户进件-微信小程序端-merchantDto-2");
        log.info(JSON.toJSONString(jsonObject));
        final String uncommittedMerchantInfoKey = String.format(RedisKey.UNCOMMITTED_MERCHANT_INFO, userInfo.getId());
        rabbitSenderService.sendReplayMerchantSubmitRemoveInfoLazyQueue(uncommittedMerchantInfoKey, 5 * 1000);
        String param = HttpUtils.format(agencyConfig, jsonObject, FunctionEnum.MERCHANT_REGISTER, merchantDto.getPayCompanyCode());
        log.info("分账商户进件-微信小程序端-请求报文: {}", param);
        String response = HttpsMain.httpsReq(MiddlewareConfig.MerchantRegists, param);
        log.info("分账商户进件-微信小程序端-响应报文: {}", response);
        final Map<String, Object> result = HttpUtils.getResultData(response);
        log.info("分账商户进件-微信小程序端-响应报文result: {}", result);
        if (RequestStatus.SUCCESS.getCode().equals(result.get("status")) && RequestStatus.SUCCESS_CODE.getCode().equals(result.get("code"))) {
            Map<String, String> resMap = (Map<String, String>) result.get("data");
            log.info("分账商户进件-微信小程序端-resMap: {}", resMap);
            Merchant merchant = new Merchant();
            MerchantVo merchantVo = merchantDao.findMerchantByOutTradeNo(merchant);
            log.info("分账商户进件-微信小程序端-merchantVo: {}", JSON.toJSONString(merchantVo));
            if (StringUtils.isEmpty(merchantVo)) {
                log.info("分账商户进件-微信小程序端-进入添加资质编号");
                // 添加资质编号
                Qualification qualification = new Qualification();
                qualification.setCertNo(resMap.get("certNo"));
                qualification.setUserId(userInfo.getId());
                qualification.setType(QualificationTypeEnum.COOPERATION_QUALIFICATION.getCode());
                if (MerchantTypeEnum.Natural.getCode().equals(merchantDto.getMerchantType())) {
                    qualification.setName(merchantDto.getPrincipalPerson());
                } else {
                    qualification.setName(merchantDto.getLegalPerson());
                }
                qualificationService.addQualification(qualification);
                // 添加商户
                merchant.setOutTradeNo(merchantDto.getOutTradeNo());
                merchant.setQualificationId(qualification.getId());
                merchant.setMerchantId(resMap.get("hlMerchantId"));
                merchant.setFeeValue(feeValue);
                merchant.setPayCompanyCode(merchantDto.getPayCompanyCode());
                merchant.setStatus(MerchantStatusEnum.AUDITING_YIHAO.getCode());
                merchant.setMerchantShortName(merchantDto.getMerchantShortName());
                merchantDao.addMerchant(merchant);
                MerchantPayCompany merchantPayCompany = new MerchantPayCompany();
                merchantPayCompany.setMchId(merchant.getId());
                merchantPayCompany.setPayCompanyCode(merchantDto.getPayCompanyCode());
                merchantPayCompany.setBankCardNo(merchantBankCard.getBankCardNo());
                merchantPayCompany.setBankCertName(merchantBankCard.getBankCertName());
                merchantPayCompanyService.addMerchantPayCompany(merchantPayCompany);
            } else {
                log.info("分账商户进件-微信小程序端-进入修改");
                merchantDao.updateMerchant(merchant);
                MerchantPayCompanyDto merchantPayCompanyDto = new MerchantPayCompanyDto();
                merchantPayCompanyDto.setMchId(merchantVo.getId());
                merchantPayCompanyDto.setPayCompanyCode(merchantDto.getPayCompanyCode());
                merchantPayCompanyDto.setBankCardNo(merchantBankCard.getBankCardNo());
                merchantPayCompanyDto.setBankCertName(merchantBankCard.getBankCertName());
                merchantPayCompanyService.update(merchantPayCompanyDto);
            }
            UserDto userDto = new UserDto();
            userDto.setId(userInfo.getId());
            userDto.setReceiptType(MchTypeEnum.OWN.getCode());
            userService.updateUserReceiptType(userDto);
            return ServerResponse.createBySuccess(merchant);
        } else {
            return ServerResponse.createByErrorMessage((String) result.get("msg"));
        }
    }

    @Override
    public ServerResponse findMerchantNameInfo(MerchantDto merchantDto) throws Exception {
        List<MerchantVo> list = merchantDao.findMerchantListByUserId(merchantDto);
        List<MerchantVo> merchantVoList = new ArrayList<>();

        Map<String, Object> form = new HashMap<>();
        for (MerchantVo merchantVo : list) {
            if (merchantVo.getStatus().equals(MerchantStatusEnum.OFF.getCode()) || merchantVo.getStatus().equals(MerchantStatusEnum.SUCCESS.getCode()) || merchantVo.getStatus().equals(MerchantStatusEnum.RISK.getCode())) {
                form.put("outTradeNo", merchantVo.getOutTradeNo());
                form.put("HlMerchantId", merchantVo.getMerchantId());
                String param = HttpUtils.format(agencyConfig, form, FunctionEnum.MERCHANT_QUERY, merchantVo.getPayCompanyCode());
                String response = HttpsMain.httpsReq(MiddlewareConfig.merchantInfo, param);
                final Map<String, Object> result = HttpUtils.getResultData(response);
                log.info("响应报文result: {}", result);
                // 支付宝微信认证信息
                if (RequestStatus.SUCCESS.getCode().equals(result.get("status")) && RequestStatus.SUCCESS_CODE.getCode().equals(result.get("code"))) {
                    Map<String, Object> resMap = (Map<String, Object>) result.get("data");
                    Map<String, Object> res = (Map<String, Object>) resMap.get("merchant");
                    Map<String, Object> merchantDetail = (Map<String, Object>) res.get("merchantDetail");
                    Map<String, Object> merchantBankCard = (Map<String, Object>) res.get("merchantBankCard");
                    Map<String, Object> form2 = new HashMap<>();
                    form2.put("HlMerchantId", merchantVo.getMerchantId());
                    String paramValue = HttpUtils.format(agencyConfig, form2, FunctionEnum.MERCHANT_REGISTER_QUERY, merchantVo.getPayCompanyCode());
                    log.info("商户注册查询接口请求报文{}", paramValue);
                    String responseValue = HttpsMain.httpsReq(MiddlewareConfig.Merchant + "/queryAuthorizeInfo", paramValue);
                    log.info("商户注册查询接口响应报文{}", responseValue);
                    if (!RsaUtil.verifyResponseSign(responseValue)) {
                        log.info("验签失败");
                        throw new ControllerException("验签失败");
                    }
                    JSONObject jsonObject = JSONObject.parseObject(responseValue);
                    Map<String, Object> data = (Map<String, Object>) jsonObject.get("data");
                    Map<String, Object> merchantData = (Map<String, Object>) data.get("merchant");
                    //同步状态值
                    Merchant editMerchant = new Merchant();
                    editMerchant.setWeChatApplymentState((String) merchantData.get("applymentState"));
                    editMerchant.setWeChatAuthorizeState((String) merchantData.get("authorizeState"));
                    editMerchant.setAliApplymentState((String) merchantData.get("aliApplymentState"));
                    editMerchant.setAliAuthorizeState((String) merchantData.get("aliAuthorizeState"));
                    editMerchant.setOutTradeNo(merchantVo.getOutTradeNo());
                    merchantDao.updateMerchant(editMerchant);
                    String timestampStr = (String) jsonObject.get("timestamp");
                    if (timestampStr != null) {
                        Long timestamp = Long.parseLong(timestampStr);
                        Date date = new Date(timestamp);

                        SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
                        String formattedDate = sdf.format(date);
                        merchantVo.setTimestamp(formattedDate);
                    }
                    PayCompany payCompany = merchantPayCompanyService.finOnePayCompany(merchantVo.getPayCompanyCode());
                    MerchantVo aliMerchantVo = new MerchantVo();

                    aliMerchantVo.setMerchantName((String) res.get("merchantName"));
                    aliMerchantVo.setRealName((String) merchantBankCard.get("bankCertName"));
                    if ("AUDIT_REJECT".equals(merchantData.get("aliApplymentState"))) {
                        aliMerchantVo.setFailReason("自动提交认证审核失败，请扫二维码手动提交认证，具体操作请参考首页底部，【新手帮助】第三个支付宝认证 教程视频完成认证。");
                    }
                    aliMerchantVo.setCertificationChannels(0);
                    if (!ObjectUtils.isEmpty(merchantData.get("smid"))) {
                        aliMerchantVo.setMerchantId((String) merchantData.get("smid"));
                        aliMerchantVo.setAliMerchId((String) merchantData.get("smid"));
                        aliMerchantVo.setAliApplymentState((String) merchantData.get("aliApplymentState"));
                        aliMerchantVo.setAliAuthorizeState((String) merchantData.get("aliAuthorizeState"));
                        if (!StringUtils.isEmpty(merchantData.get("aliQrcode"))) {
                            Color backgroundColor = Color.white; // 替换成你想要的背景色
                            aliMerchantVo.setAliQrcode(this.ImageToBase64((String) merchantData.get("aliQrcode"), backgroundColor));
                        }
                        aliMerchantVo.setTimestamp(merchantVo.getTimestamp());
                        aliMerchantVo.setStatus(merchantVo.getStatus());
                        //aliApplymentState等于AUDIT_REJECT审核失败,等于CANCELED已测回,AUDIT_FREEZE已冻结,AUDITING审核中并且支付宝没有返回二维码 返回渠道二维码
                        if (ObjectUtils.isEmpty(aliMerchantVo.getAliApplymentState()) || !ObjectUtils.isEmpty(aliMerchantVo.getAliApplymentState()) &&
                                (aliMerchantVo.getAliApplymentState().equals("AUDIT_REJECT") || aliMerchantVo.getAliApplymentState().equals("CANCELED") ||
                                        (aliMerchantVo.getAliApplymentState().equals("AUDIT_FREEZE") || aliMerchantVo.getAliApplymentState().equals("AUDITING")) && ObjectUtils.isEmpty(aliMerchantVo.getAliQrcode()))) {
                            aliMerchantVo.setChannelCode(payCompany.getAlipayChatCertificationCode());
                        }
                        if (merchantDto.getAppState() == 1 && aliMerchantVo.getAliAuthorizeState().equals("AUTHORIZED")) {
                            merchantVoList.add(aliMerchantVo);
                        } else if (merchantDto.getAppState() == 0 && aliMerchantVo.getAliAuthorizeState().equals("UNAUTHORIZED")) {
                            merchantVoList.add(aliMerchantVo);
                        }
                    }

                    MerchantVo weChatMerchantVo = new MerchantVo();
                    weChatMerchantVo.setMerchantName((String) res.get("merchantName"));
                    weChatMerchantVo.setRealName((String) merchantBankCard.get("bankCertName"));
                    if ("APPLYMENT_STATE_REJECTED".equals(merchantData.get("applymentState"))) {
                        weChatMerchantVo.setFailReason("自动提交认证审核失败，请扫二维码手动提交认证，具体操作请参考首页底部，【新手帮助】第二个微信认证 教程视频完成认证。");
                    }
                    weChatMerchantVo.setCertificationChannels(1);
                    if (!ObjectUtils.isEmpty(merchantData.get("wechatMerchId"))) {
                        weChatMerchantVo.setMerchantId((String) merchantData.get("wechatMerchId"));
                        weChatMerchantVo.setWechatMerchId((String) merchantData.get("wechatMerchId"));
                        weChatMerchantVo.setWeChatApplymentState((String) merchantData.get("applymentState"));
                        weChatMerchantVo.setQrcodeData((String) merchantData.get("qrcodeData"));
                        weChatMerchantVo.setWeChatAuthorizeState((String) merchantData.get("authorizeState"));
                        weChatMerchantVo.setStatus(merchantVo.getStatus());
                        weChatMerchantVo.setTimestamp(merchantVo.getTimestamp());
                        //applymentState等于APPLYMENT_STATE_REJECTED审核失败,APPLYMENT_STATE_CANCELED已作废(撤销),APPLYMENT_STATE_FREEZED已冻结,APPLYMENT_STATE_WAITTING_FOR_AUDIT审核中并且微信没有返回二维码   返回渠道二维码
                        if (ObjectUtils.isEmpty(weChatMerchantVo.getWeChatApplymentState()) || !ObjectUtils.isEmpty(weChatMerchantVo.getWeChatApplymentState()) &&
                                (weChatMerchantVo.getWeChatApplymentState().equals("APPLYMENT_STATE_REJECTED") || weChatMerchantVo.getWeChatApplymentState().equals("APPLYMENT_STATE_CANCELED") ||
                                        ((weChatMerchantVo.getWeChatApplymentState().equals("APPLYMENT_STATE_FREEZED") || weChatMerchantVo.getWeChatApplymentState().equals("APPLYMENT_STATE_WAITTING_FOR_AUDIT")) && ObjectUtils.isEmpty(weChatMerchantVo.getQrcodeData())))) {
                            weChatMerchantVo.setChannelCode(payCompany.getWeChatCertificationCode());
                        }
                        if (merchantDto.getAppState() == 1 && weChatMerchantVo.getWeChatAuthorizeState().equals("AUTHORIZE_STATE_AUTHORIZED")) {
                            merchantVoList.add(weChatMerchantVo);
                        } else if (merchantDto.getAppState() == 0 && weChatMerchantVo.getWeChatAuthorizeState().equals("AUTHORIZE_STATE_UNAUTHORIZED")) {
                            merchantVoList.add(weChatMerchantVo);
                        }
                    }
                }

            }
        }
        return ServerResponse.createBySuccess(merchantVoList);
    }

    @Override
    public PageInfo findComplainData(MerchantDto merchantDto) throws Exception {
        List<MerchantVo> list = merchantDao.findMerchantListByUserId(merchantDto);
        List<String> merchantIdList = new ArrayList<>();
        PageInfo pageInfo = null;
        for (MerchantVo merchantVo : list) {
            merchantIdList.add(merchantVo.getMerchantId());
        }

//        merchantIdList.add("E1806622445");//测试写死

        Map<String, Object> form = new HashMap<>();
        form.put("startDate", merchantDto.getStartDate());
        form.put("endDate", merchantDto.getEndDate());
        form.put("merchantIdList", merchantIdList);
        form.put("pageNum", merchantDto.getPageNum());
        form.put("pageSize", merchantDto.getPageSize());
//        form.put("merchantId", merchantDto.getMerchantId());
        form.put("keyword", merchantDto.getContent());

        String param = HttpUtils.format(agencyConfig, form, FunctionEnum.COMPLAINT_LIST_INFO, merchantDto.getPayCompanyCode());
        String response = HttpsMain.httpReq(MiddlewareConfig.Merchant + "/complaint", param);
        final Map<String, Object> result = HttpUtils.getResultData(response);
        log.info("响应报文result: {}", result);
        if (RequestStatus.SUCCESS.getCode().equals(result.get("status")) && RequestStatus.SUCCESS_CODE.getCode().equals(result.get("code"))) {
            Map<String, Object> resMap = (Map<String, Object>) result.get("data");
            List<MerchantComplaintVo> listItem = (List<MerchantComplaintVo>) resMap.get("list");
            int pageNum = (int) resMap.get("pageNum");
            int pageSize = (int) resMap.get("pageSize");
            int pages = (int) resMap.get("pages");
            int total = (int) resMap.get("total");
            pageInfo = new PageInfo(listItem);
            pageInfo.setPageNum(pageNum);
            pageInfo.setPageSize(pageSize);
            pageInfo.setTotal(total);
            pageInfo.setPages(pages);

        } else {
            log.info("中间件查询投诉列表报错");
            throw new ControllerException("查询投诉列表错误:" + (String) result.get("msg"));
        }
        return pageInfo;
    }

    @Override
    public ServerResponse findMerchantComplaintContent(MerchantDto merchantDto) throws Exception {
        if (merchantDto.getMchComplaintId() == null) {
            return ServerResponse.createByErrorMessage("该投诉已完成或不存在");
        }
        List<MerchantComplaintResVo> listItem = new ArrayList<>();
        Map<String, Object> form = new HashMap<>();
        form.put("mchComplaintId", merchantDto.getMchComplaintId());

        String param = HttpUtils.format(agencyConfig, form, FunctionEnum.COMPLAINT_CONTENT_INFO, merchantDto.getPayCompanyCode());
        String response = HttpsMain.httpReq(MiddlewareConfig.Merchant + "/complaint", param);
        final Map<String, Object> result = HttpUtils.getResultData(response);
        log.info("响应报文result: {}", result);
        if (RequestStatus.SUCCESS.getCode().equals(result.get("status")) && RequestStatus.SUCCESS_CODE.getCode().equals(result.get("code"))) {
            Map<String, Object> resMap = (Map<String, Object>) result.get("data");
            listItem = (List<MerchantComplaintResVo>) resMap.get("list");
        } else {
            log.info("中间件查询投诉信息报错");
            ServerResponse.createByErrorMessage("查询投诉信息错误:" + result.get("msg"));
        }
        return ServerResponse.createBySuccess(listItem);
    }

    @Override
    public ServerResponse complaintResponse(MerchantDto merchantDto) throws Exception {
        if (merchantDto.getComplaintId() == null) {
            return ServerResponse.createByErrorMessage("投诉订单不存在");
        }
        if (merchantDto.getHlMerchantId() == null) {
            return ServerResponse.createByErrorMessage("缺少商户号");
        }
        List<MerchantVo> list = merchantDao.findMerchantListByUserId(merchantDto);
        boolean flag = false;
        for (MerchantVo merchantVo : list) {
            if (merchantVo.getMerchantId().equals(merchantDto.getHlMerchantId())) {
                flag = true;
                break;
            }
        }
        if (flag) {
            Map<String, Object> form = new HashMap<>();
            form.put("complaintId", merchantDto.getComplaintId());
            form.put("hlMerchantId", merchantDto.getHlMerchantId());
            form.put("responseContent", merchantDto.getResponseContent());
            form.put("responseImages", merchantDto.getResponseImages());
            form.put("operator", !ObjectUtils.isEmpty(merchantDto.getUserInfo().getName()) ? merchantDto.getUserInfo().getName() : merchantDto.getUserInfo().getNickname());

            String param = HttpUtils.format(agencyConfig, form, FunctionEnum.MERCHANT_COMPLAINT_RESPONSE_V2, merchantDto.getPayCompanyCode());
            String response = HttpsMain.httpReq(MiddlewareConfig.Merchant + "/complaint", param);
            final Map<String, Object> result = HttpUtils.getResultData(response);
            log.info("响应报文result: {}", result);
            if (RequestStatus.SUCCESS.getCode().equals(result.get("status")) && RequestStatus.SUCCESS_CODE.getCode().equals(result.get("code"))) {
                return ServerResponse.createBySuccess();
            } else {
                return ServerResponse.createByErrorMessage((String) result.get("msg"));
            }
        } else {
            return ServerResponse.createByErrorMessage("该投诉不属于此商户");
        }

    }

    @Override
    public ServerResponse complaintComplete(MerchantDto merchantDto) throws Exception {
        if (merchantDto.getComplaintId() == null) {
            return ServerResponse.createByErrorMessage("投诉订单不存在");
        }
        if (merchantDto.getHlMerchantId() == null) {
            return ServerResponse.createByErrorMessage("缺少商户号");
        }
        List<MerchantVo> list = merchantDao.findMerchantListByUserId(merchantDto);
        boolean flag = false;
        for (MerchantVo merchantVo : list) {
            if (merchantVo.getMerchantId().equals(merchantDto.getHlMerchantId())) {
                flag = true;
                break;
            }
        }
        if (flag) {
            Map<String, Object> form = new HashMap<>();
            form.put("complaintId", merchantDto.getComplaintId());
            form.put("complaintHandleState", merchantDto.getComplaintHandleState());
            form.put("responseImages", merchantDto.getResponseImages());
            form.put("hlMerchantId", merchantDto.getHlMerchantId());
            form.put("operator", !ObjectUtils.isEmpty(merchantDto.getUserInfo().getName()) ? merchantDto.getUserInfo().getName() : merchantDto.getUserInfo().getNickname());

            String param = HttpUtils.format(agencyConfig, form, FunctionEnum.MERCHANT_COMPLAINT_COMPLETE_V2, merchantDto.getPayCompanyCode());
            String response = HttpsMain.httpReq(MiddlewareConfig.Merchant + "/complaint", param);
            final Map<String, Object> result = HttpUtils.getResultData(response);
            log.info("响应报文result: {}", result);
            if (RequestStatus.SUCCESS.getCode().equals(result.get("status")) && RequestStatus.SUCCESS_CODE.getCode().equals(result.get("code"))) {
                return ServerResponse.createBySuccess();
            } else {
                return ServerResponse.createByErrorMessage((String) result.get("msg"));
            }
        } else {
            return ServerResponse.createByErrorMessage("该投诉不属于此商户");
        }
    }

    public String ImageToBase64(String imageUrl, Color backgroundColor) {
        try {
            URL url = new URL(imageUrl);
            HttpURLConnection connection = (HttpURLConnection) url.openConnection();
            connection.setRequestMethod("GET");
            connection.connect();
            InputStream in = connection.getInputStream();
            BufferedImage originalImage = ImageIO.read(in);

            // 创建一个新的BufferedImage，并指定背景色
            BufferedImage newImage = new BufferedImage(originalImage.getWidth(), originalImage.getHeight(), BufferedImage.TYPE_INT_RGB);
            Graphics2D graphics = newImage.createGraphics();
            graphics.setColor(backgroundColor);
            graphics.fillRect(0, 0, newImage.getWidth(), newImage.getHeight());
            graphics.drawImage(originalImage, 0, 0, null);
            graphics.dispose();

            // 转换为Base64编码
            ByteArrayOutputStream baos = new ByteArrayOutputStream();
            ImageIO.write(newImage, "jpg", baos);
            baos.flush();
            String base64Image = Base64.getEncoder().encodeToString(baos.toByteArray());
            baos.close();

            return base64Image;
        } catch (Exception e) {
            e.printStackTrace();
        }
        return imageUrl;
    }

    @Override
    public ServerResponse findIdWhetherToImportBusiness(UserInfo userInfo) throws IOException, NoSuchAlgorithmException, NoSuchProviderException, KeyManagementException {
        MerchantDto merchantDto = new MerchantDto();
        merchantDto.setUserInfo(userInfo);
        merchantDto.setUserId(userInfo.getId());
        merchantDto.setType(QualificationTypeEnum.MAIN_QUALIFICATIONS.getCode());
        List<MerchantVo> list = merchantDao.findMerchantListByUserId(merchantDto);
        if (!ObjectUtils.isEmpty(list) && list.size() > 0) {
            //是否所有商户都被拒绝
            boolean allStatusEqualsFail = list.stream().allMatch(merchant -> merchant.getStatus().equals(MerchantStatusEnum.FAIL.getCode()) || merchant.getStatus().equals(MerchantStatusEnum.GO_BACK.getCode()));
            if (allStatusEqualsFail) {
                return ServerResponse.createBySuccess("business", true);//所有商户都被拒绝
            }
            for (MerchantVo m : list) {
                // 支付宝微信认证信息
                Map<String, Object> form2 = new HashMap<>();
                form2.put("HlMerchantId", m.getMerchantId());
                String paramValue = HttpUtils.format(agencyConfig, form2, FunctionEnum.MERCHANT_REGISTER_QUERY, m.getPayCompanyCode());
                log.info("商户注册查询接口请求报文{}", paramValue);
                String responseValue = HttpsMain.httpsReq(MiddlewareConfig.Merchant + "/queryAuthorizeInfo", paramValue);
                log.info("商户注册查询接口响应报文{}", responseValue);
                if (!RsaUtil.verifyResponseSign(responseValue)) {
                    log.info("验签失败");
                    throw new ControllerException("验签失败");
                }
                JSONObject jsonObject = JSONObject.parseObject(responseValue);
                Map<String, Object> data = (Map<String, Object>) jsonObject.get("data");
                Map<String, Object> merchantData = (Map<String, Object>) data.get("merchant");
                if (merchantData.get("status").equals(MerchantStatusEnum.SUCCESS.getCode())) {
                    if (ObjectUtils.isEmpty(merchantData.get("smid")) || (!ObjectUtils.isEmpty(merchantData.get("aliAuthorizeState")) && merchantData.get("aliAuthorizeState").equals("AUTHORIZED")) &&
                            (!ObjectUtils.isEmpty(merchantData.get("authorizeState")) && merchantData.get("authorizeState").equals("AUTHORIZE_STATE_AUTHORIZED"))) {
                        return ServerResponse.createBySuccess("collection", true);//已认证微信 支付宝
                    }
                }
            }
            return ServerResponse.createBySuccess("collection", false);//未认证微信 支付宝
        } else {
            return ServerResponse.createBySuccess("business", false);//账号未进件商户
        }
    }

    @Override
    public MerchantVo findMerchantByOutTradeNo(Merchant merchant) {
        return merchantDao.findMerchantByOutTradeNo(merchant);
    }

    @Override
    public Integer addMerchant(Merchant merchant) {
        return merchantDao.addMerchant(merchant);
    }

    @Override
    public Integer updateMerchant(Merchant merchant) {
        return merchantDao.updateMerchant(merchant);
    }

    // 签约其他渠道
    @Override
    public ServerResponse merchantReRegistration(MerchantDto merchantDto, UserInfo userInfo) throws IOException, NoSuchAlgorithmException, NoSuchProviderException, KeyManagementException {
        // 判断商户订单号是否存
        if (StringUtils.isEmpty(merchantDto.getOutTradeNo()) || StringUtils.isEmpty(merchantDto.getPayCompanyCode())) {
            return ServerResponse.createByErrorMessage("订单号或支付渠道不存在，请重新操作");
        }
        List<MerchantFeeParamDto> feeParamList = new ArrayList<>();
        //费率
        feeParamList.add(new MerchantFeeParamDto(PayChannelEnum.WX.getChnCode(), MerchantFeeTypeEnum.T1.getFeeCode(), feeValue));
        feeParamList.add(new MerchantFeeParamDto(PayChannelEnum.Ali.getChnCode(), MerchantFeeTypeEnum.T1.getFeeCode(), feeValue));
        merchantDto.setPath(configProperties.getClientBackEndUrl() + "/");
        int random = (int) (Math.random() * 900 + 100);
        String email = String.valueOf(System.currentTimeMillis()) + random + "@qq.com";
        merchantDto.setEmail(email);
        JSONObject jsonObject = JSONObject.parseObject(JSON.toJSONString(merchantDto), Feature.OrderedField);
        jsonObject.put("merchantFeeList", feeParamList);

        String param = HttpUtils.format(agencyConfig, jsonObject, FunctionEnum.MERCHANT_RE_REGISTRATION, merchantDto.getPayCompanyCode());
        log.info("请求报文: {}", param);
        String response = HttpsMain.httpsReq(MiddlewareConfig.MerchantRegists, param);
        log.info("响应报文: {}", response);
        final Map<String, Object> result = HttpUtils.getResultData(response);
        log.info("响应报文result: {}", result);
        if (RequestStatus.SUCCESS.getCode().equals(result.get("status")) && RequestStatus.SUCCESS_CODE.getCode().equals(result.get("code"))) {
            Map<String, String> resMap = (Map<String, String>) result.get("data");
            Merchant merchant = new Merchant();
            merchant.setOutTradeNo(merchantDto.getOutTradeNo());
            MerchantVo merchantVo = merchantDao.findMerchantByOutTradeNo(merchant);
            MerchantPayCompany merchantPayCompany = new MerchantPayCompany();
            merchantPayCompany.setMchId(merchantVo.getId());
            merchantPayCompany.setPayCompanyCode(merchantDto.getPayCompanyCode());
            merchantPayCompany.setBankCardNo(merchantDto.getBankCardNo());
            merchantPayCompany.setBankCertName(merchantDto.getBankCertName());
            merchantPayCompanyService.addMerchantPayCompany(merchantPayCompany);
            return ServerResponse.createBySuccess();
        } else {
            return ServerResponse.createByErrorMessage((String) result.get("msg"));
        }
    }

    @Override
    public ServerResponse switchoverPayCompany(MerchantDto merchantDto) throws IOException, NoSuchAlgorithmException, NoSuchProviderException, KeyManagementException {
        // 判断商户订单号是否存
        if (StringUtils.isEmpty(merchantDto.getMerchantId()) || StringUtils.isEmpty(merchantDto.getPayCompanyCode())) {
            return ServerResponse.createByErrorMessage("商户号或支付渠道不存在，请重新操作");
        }
        Map<String, Object> form = new HashMap<>();
        form.put("HlMerchantId", merchantDto.getMerchantId());
        String param = HttpUtils.format(agencyConfig, form, FunctionEnum.SWITCHOVER_PAY_COMPANY, merchantDto.getPayCompanyCode());
        String response = HttpsMain.httpsReq(MiddlewareConfig.switchoverPayCompany, param);
        log.info("请求响应结果{}", response);
        //延签并返回map值
        final Map<String, Object> result = HttpUtils.getResultData(response);
        final String status = (String) result.get("status");
        final String code = (String) result.get("code");
        if (status.equals(RequestStatus.SUCCESS.getCode()) && code.equals(RequestStatus.SUCCESS_CODE.getCode())) {
            Merchant merchant = new Merchant();
            merchant.setPayCompanyCode(merchantDto.getPayCompanyCode());
            merchant.setOutTradeNo(merchantDto.getOutTradeNo());
            merchantDao.updateMerchant(merchant);
            // 根据商户号查询已绑定的商户
            List<MerchantStoreVo> MerchantStoreVoList = merchantStoreService.findAllMerchantStoreByMerchantId(merchantDto.getMerchantId());
            for (MerchantStoreVo merchantStoreVo : MerchantStoreVoList) {
                redisTemplate.delete(String.format(RedisKey.MERCHANT_STORE, merchantStoreVo.getId()));
            }
            return ServerResponse.createBySuccess((String) result.get("msg"));
        } else {
            return ServerResponse.createByErrorMessage((String) result.get("msg"));
        }
    }

    @Override
    public ServerResponse updateSplit(MerchantDto merchantDto) throws Exception {
        //组装参数 请求中间件 根据支付公司请求
        Map<String, Object> form = new HashMap<>();
        form.put("hlMerchantId", merchantDto.getMerchantId());
        form.put("authTypes", merchantDto.getAuthTypes());
        String param = HttpUtils.format(agencyConfig, form, FunctionEnum.MERCHANT_OPEN_SPLIT, merchantDto.getPayCompanyCode());
        String response = HttpsMain.httpsReq(MiddlewareConfig.Merchant, param);
        log.info("请求响应结果{}", response);
        //延签并返回map值
        final Map<String, Object> result = HttpUtils.getResultData(response);
        final String status = (String) result.get("status");
        final String code = (String) result.get("code");
        if (status.equals(RequestStatus.SUCCESS.getCode()) && code.equals(RequestStatus.SUCCESS_CODE.getCode())) {
//            String data = JSONObject.toJSONString(result.get("data"));
            return ServerResponse.createBySuccess(result.get("data"));
        } else {
            throw new ControllerException((String) result.get("msg"));
        }
    }

    @Override
    public ServerResponse sendCode(MerchantDto merchantDto) throws Exception {
        Map<String, Object> form = new HashMap<>();
        form.put("hlMerchantId", merchantDto.getMerchantId());
        form.put("authTypes", merchantDto.getAuthTypes());
        form.put("phone", merchantDto.getPhone());
        form.put("bankCardNo", merchantDto.getBankCardNo());
        String param = HttpUtils.format(agencyConfig, form, FunctionEnum.MERCHANT_GAIN_OPEN_SPLIT_SENDCODE, merchantDto.getPayCompanyCode());
        String response = HttpsMain.httpsReq(MiddlewareConfig.Merchant, param);
        log.info("请求响应结果{}", response);
        //延签并返回map值
        final Map<String, Object> result = HttpUtils.getResultData(response);
        final String status = (String) result.get("status");
        final String code = (String) result.get("code");
        if (status.equals(RequestStatus.SUCCESS.getCode()) && code.equals(RequestStatus.SUCCESS_CODE.getCode())) {
            return ServerResponse.createBySuccess((String) result.get("msg"));
        } else {
            return ServerResponse.createByErrorMessage((String) result.get("msg"));
        }
    }

    @Override
    public ServerResponse codeVerify(MerchantDto merchantDto) throws Exception {
        Map<String, Object> form = new HashMap<>();
        form.put("hlMerchantId", merchantDto.getMerchantId());
        form.put("authTypes", merchantDto.getAuthTypes());
        form.put("phone", merchantDto.getPhone());
        form.put("bankCardNo", merchantDto.getBankCardNo());
        form.put("smsCode", merchantDto.getSmsCode());
        form.put("money", merchantDto.getMoney());
        String param = HttpUtils.format(agencyConfig, form, FunctionEnum.MERCHANT_OPEN_SPLIT_VERIFY, merchantDto.getPayCompanyCode());
        String response = HttpsMain.httpsReq(MiddlewareConfig.Merchant, param);
        log.info("请求响应结果{}", response);
        //延签并返回map值
        final Map<String, Object> result = HttpUtils.getResultData(response);
        final String status = (String) result.get("status");
        final String code = (String) result.get("code");
        if (status.equals(RequestStatus.SUCCESS.getCode()) && code.equals(RequestStatus.SUCCESS_CODE.getCode())) {
            Merchant merchant = merchantDao.findMerchantByMerchantId(merchantDto.getMerchantId());
            MerchantPayCompanyDto merchantPayCompanyDto = new MerchantPayCompanyDto();
            merchantPayCompanyDto.setMchId(merchant.getId());
            merchantPayCompanyDto.setPayCompanyCode(merchantDto.getPayCompanyCode());
            merchantPayCompanyDto.setOpenSplitStatus(1);
            merchantPayCompanyService.update(merchantPayCompanyDto);
            return ServerResponse.createBySuccess((String) result.get("msg"));
        } else {
            return ServerResponse.createByErrorMessage((String) result.get("msg"));
        }
    }

    @Override
    public MerchantVo findByUserIdAndMerchantId(MerchantDto merchantDto) {
        return merchantDao.findByUserIdAndMerchantId(merchantDto);
    }


    @Override
    public ServerResponse updateBankCard(MerchantDto merchantDto) throws IOException, NoSuchAlgorithmException, NoSuchProviderException, KeyManagementException {
        Merchant merchant = new Merchant();
        merchant.setOutTradeNo(merchantDto.getOutTradeNo());
        MerchantVo merchantVo = merchantDao.findMerchantByOutTradeNo(merchant);
        if (StringUtils.isEmpty(merchantVo)) {
            return ServerResponse.createByErrorMessage("获取参数有误，请重新操作");
        }

        Map<String, Object> form = new HashMap<>();
        form.put("outTradeNo", UUID.randomUUID().toString());
        form.put("hlMerchantId", merchantDto.getMerchantId());

        Map<String, Object> bankCard = new HashMap<>();
        merchantDto.setOutTradeNo(UUID.randomUUID().toString());
        bankCard.put("bankCardNo", merchantDto.getBankCardNo());
        bankCard.put("bankCertName", merchantDto.getBankCertName());
        bankCard.put("accountType", merchantDto.getAccountType());
        bankCard.put("bankName", merchantDto.getBankName());
        bankCard.put("contactLine", merchantDto.getContactLine());
        bankCard.put("bankCardA", merchantDto.getBankCardA());
        JSONObject jsonObject = JSONObject.parseObject(JSON.toJSONString(form), Feature.OrderedField);
        jsonObject.put("merchantBankCard", bankCard);
        String param = HttpUtils.format(agencyConfig, jsonObject, FunctionEnum.MERCHANT_UPDATE, merchantDto.getPayCompanyCode());
        String response = HttpsMain.httpsReq(MiddlewareConfig.Merchant, param);
        log.info("请求响应结果{}", response);
        //延签并返回map值
        final Map<String, Object> result = HttpUtils.getResultData(response);
        final String status = (String) result.get("status");
        final String code = (String) result.get("code");
        if (status.equals(RequestStatus.SUCCESS.getCode()) && code.equals(RequestStatus.SUCCESS_CODE.getCode())) {
            MerchantPayCompanyDto merchantPayCompanyDto = new MerchantPayCompanyDto();
            merchantPayCompanyDto.setMchId(merchantVo.getId());
            merchantPayCompanyDto.setPayCompanyCode(merchantDto.getPayCompanyCode());
            merchantPayCompanyDto.setBankCardNo(merchantDto.getBankCardNo());
            merchantPayCompanyDto.setBankCertName(merchantDto.getBankCertName());
            merchantPayCompanyService.update(merchantPayCompanyDto);
            return ServerResponse.createBySuccess("修改成功");
        } else {
            return ServerResponse.createByErrorMessage((String) result.get("msg"));
        }
    }

    @Override
    public ServerResponse updateMerchantShortName(MerchantDto merchantDto) throws IOException, NoSuchAlgorithmException, NoSuchProviderException, KeyManagementException {

        if (StringUtils.isEmpty(merchantDto.getMerchantId())) {
            return ServerResponse.createByErrorMessage("商户号不能为空");
        }

        String merchantShortName = merchantDto.getMerchantShortName().trim().replaceAll(" ", "");
        if (StringUtils.isEmpty(merchantShortName)) {
            return ServerResponse.createByErrorMessage("新收款名称不能为空");
        }

        Map<String, Object> form = new HashMap<>();
        form.put("outTradeNo", UUID.randomUUID().toString());
        form.put("hlMerchantId", merchantDto.getMerchantId());
        Map<String, Object> merchantDetail = new HashMap<>();
        merchantDetail.put("alias", merchantShortName);
        JSONObject jsonObject = JSONObject.parseObject(JSON.toJSONString(form), Feature.OrderedField);
        jsonObject.put("merchantDetail", merchantDetail);
        String param = HttpUtils.format(agencyConfig, jsonObject, FunctionEnum.MERCHANT_UPDATE, merchantDto.getPayCompanyCode());
        String response = HttpsMain.httpsReq(MiddlewareConfig.Merchant, param);
        log.info("请求响应结果{}", response);
        //延签并返回map值
        final Map<String, Object> result = HttpUtils.getResultData(response);
        if (RequestStatus.SUCCESS.getCode().equals(result.get("status")) && RequestStatus.SUCCESS_CODE.getCode().equals(result.get("code"))) {
            Merchant merchant = new Merchant();
            merchant.setOutTradeNo(merchantDto.getOutTradeNo());
            merchant.setMerchantShortName(merchantShortName);
            merchantDao.updateMerchant(merchant);
            return ServerResponse.createBySuccess("修改成功");
        } else {
            return ServerResponse.createByErrorMessage((String) result.get("msg"));
        }
    }

    /**
     * 获取商户上传的资料（未上传）
     *
     * @param userInfo
     * @return
     */
    @Override
    public ServerResponse getUncommittedMerchantInfo(UserInfo userInfo) {
        try {
            final String uncommittedMerchantInfoKey = String.format(RedisKey.UNCOMMITTED_MERCHANT_INFO, userInfo.getId());
            MerchantDto merchantDto = (MerchantDto) redisTemplate.opsForValue().get(uncommittedMerchantInfoKey);

            if (StringUtils.isEmpty(merchantDto)) {
                return ServerResponse.createBySuccess();
            }
            return ServerResponse.createBySuccess(merchantDto);
        } catch (Exception e) {
            e.printStackTrace();
            errorLogCommonService.writerInfoException("获取商户上传的资料（未上传）不成功", e, null);
            return ServerResponse.createBySuccess();
        }
    }

    /**
     * 商户上传的资料（未上传）
     *
     * @param userInfo
     * @param merchantDto
     * @return
     */
    @Override
    public ServerResponse updateUncommittedMerchantInfo(UserInfo userInfo, MerchantDto merchantDto) {
        final String uncommittedMerchantInfoKey = String.format(RedisKey.UNCOMMITTED_MERCHANT_INFO, userInfo.getId());
        CompletableFuture<Void> future1 = CompletableFuture.runAsync(() -> {
            redisTemplate.opsForValue().set(uncommittedMerchantInfoKey, merchantDto, 7, TimeUnit.DAYS);
        }, executor);
        return ServerResponse.createBySuccess();
    }

    /**
     * 获取分账商户上传的资料（未上传）
     *
     * @param userInfo
     * @return
     */
    @Override
    public ServerResponse getUncommittedSubAccountMerchantInfo(UserInfo userInfo) {
        try {
            final String uncommittedSubAccountMerchantInfoKey = String.format(RedisKey.UNCOMMITTED_SUBACCOUNT_MERCHANT_INFO, userInfo.getId());
            MerchantDto merchantDto = (MerchantDto) redisTemplate.opsForValue().get(uncommittedSubAccountMerchantInfoKey);

            if (StringUtils.isEmpty(merchantDto)) {
                return ServerResponse.createBySuccess();
            }
            return ServerResponse.createBySuccess(merchantDto);
        } catch (Exception e) {
            e.printStackTrace();
            errorLogCommonService.writerInfoException("获取商户上传的资料（未上传）不成功", e, null);
            return ServerResponse.createBySuccess();
        }
    }

    /**
     * 修改商户上传的资料（未上传）
     *
     * @param userInfo
     * @param merchantDto
     * @return
     */
    @Override
    public ServerResponse updateUncommittedSubAccountMerchantInfo(UserInfo userInfo, MerchantDto merchantDto) {
        final String uncommittedSubAccountMerchantInfoKey = String.format(RedisKey.UNCOMMITTED_SUBACCOUNT_MERCHANT_INFO, userInfo.getId());
        redisTemplate.opsForValue().set(uncommittedSubAccountMerchantInfoKey, merchantDto, 7, TimeUnit.DAYS);
        return ServerResponse.createBySuccess();
    }

    /**
     * 各类进件图片上传接口-小程序
     *
     * @param file
     * @param photoType
     * @return
     */
    @Override
    public ServerResponse merchantRegisterUploadByApplet(MultipartFile file, String photoType) throws Exception {

        /**
         * 错误码：
         * 1：未知错误
         * 10001：上传失败
         * 10002：识别失败
         */

        /**
         * 把图片上传到中间件商户模块-begin
         */
        Map<String, Object> bizMap = new HashMap<>();

        bizMap.put("outTradeNo", UUID.randomUUID().toString());
        String bizContent = JSON.toJSONString(bizMap);
        Map<String, String> map = new TreeMap<>();
        log.info("各类进件图片上传接口-小程序：" + bizContent);
        map.put("content", bizContent);
        map.put("function", FunctionEnum.MERCHANT_UPLOADPHOTO.getCode());
        // 请求时间戳,时区为GMT+8(北京时间)
        map.put("timestamp", new Timestamp(System.currentTimeMillis()).toString());
        //系统参数
        map.put("agencyNo", agencyConfig.getIsvOrgId());// 授权用户名(固定值)
        final String signStr = JSON.toJSONString(map, SerializerFeature.SortField);
        final String sign = RsaUtil.sign(signStr, agencyConfig.getPrivateKey());
        map.put("sign", sign);

        MultipartEntityBuilder entityBuilder = MultipartEntityBuilder.create();
        entityBuilder.addBinaryBody("picture", file.getInputStream(), ContentType.DEFAULT_BINARY, file.getName()).build();
        for (Map.Entry<String, String> entry : map.entrySet()) {
            entityBuilder.addPart(entry.getKey(), new StringBody(entry.getValue()));
        }

        HttpEntity reqEntity = entityBuilder.build();
        String response = HttpsMain.httpPost(MiddlewareConfig.uploadUrl, reqEntity);
        log.info("响应报文: {}", response);
        final Map<String, Object> result = HttpUtils.getResultData(response);
        log.info("响应报文result: {}", result);

        if (!RequestStatus.SUCCESS.getCode().equals(result.get("status")) || !RequestStatus.SUCCESS_CODE.getCode().equals(result.get("code"))) {
            return ServerResponse.createByErrorCodeMessage(MerchantRegisterUploadByApplet.UPLOAD_FAIL.getCode(), (String) result.get("msg"));
        }
        /**
         * 把图片上传到中间件商户模块-end
         */


        /**
         * 上传成功后识别图片-begin
         */
        MyBankPhotoDto myBankPhotoDto = new MyBankPhotoDto();

        Map<String, String> resMap = (Map<String, String>) result.get("data");
        final String fileName = resMap.get("photoUrl");
        myBankPhotoDto.setPicture(fileName);
        try {
            final String imgUrl = qiniuProperties.getImgUrl() + fileName + ".jpg";
            if (PhotoType.CERT_PHOTO_A.equals(photoType)) {
                JSONObject idCertNo = baiduApiService.getIdentityPeriod(fileName, imgUrl, Integer.valueOf(PhotoType.CERT_PHOTO_A));
                if (!BaiduImageStatusEnum.NORMAL.getCode().equals(idCertNo.get("imageStatus"))) {
                    return ServerResponse.createByErrorCodeMessage(
                            MerchantRegisterUploadByApplet.FAILURE_TO_IDENTIFY.getCode(),
                            idCertNo.getString("msg"),
                            myBankPhotoDto
                    );
                }
                myBankPhotoDto.setPrincipalPerson(idCertNo.getString("name"));
                myBankPhotoDto.setPrincipalCertNo(idCertNo.getString("certNo"));
            } else if (PhotoType.CERT_PHOTO_B.equals(photoType)) {
                JSONObject idCertNo = baiduApiService.getIdentityPeriod(fileName, imgUrl, Integer.valueOf(PhotoType.CERT_PHOTO_B));
                if (!BaiduImageStatusEnum.NORMAL.getCode().equals(idCertNo.get("imageStatus"))) {
                    return ServerResponse.createByErrorCodeMessage(
                            MerchantRegisterUploadByApplet.FAILURE_TO_IDENTIFY.getCode(),
                            idCertNo.getString("msg"),
                            myBankPhotoDto
                    );
                }
                myBankPhotoDto.setPrincipalCertNoStartDate((String) idCertNo.get("staData"));
                myBankPhotoDto.setPrincipalCertNoExpDate((String) idCertNo.get("endData"));
            } else if (PhotoType.LICENSE_PHOTO.equals(photoType)) {
                JSONObject idCertNo = baiduApiService.getBusiness(fileName, imgUrl);
                if (org.apache.commons.lang.StringUtils.isBlank((String) idCertNo.get("staData")) || "无".equals((String) idCertNo.get("staData"))) {
                    return ServerResponse.createByErrorCodeMessage(
                            MerchantRegisterUploadByApplet.FAILURE_TO_IDENTIFY.getCode(),
                            "识别不成功，请上传清晰营业执照",
                            myBankPhotoDto
                    );
                }
                myBankPhotoDto.setLegalPerson(idCertNo.getString("businessName"));
                myBankPhotoDto.setBussStartDate(idCertNo.getString("staData"));
                String endData = idCertNo.getString("endData");
                if ("无".equals(idCertNo.getString("endData"))) {
                    endData = "长期";
                }
                myBankPhotoDto.setBussExpDate(endData);
                myBankPhotoDto.setBussAuthNum(idCertNo.getString("bussAuthNum"));
            } else if (PhotoType.BANK_CARD_A.equals(photoType)) {
                JSONObject jsonBuss = baiduApiService.getBankCard(fileName, imgUrl);
                String bankCardNumber = (String) jsonBuss.get("bankCardNumber");
                if (org.apache.commons.lang.StringUtils.isBlank(bankCardNumber) || "无".equals(bankCardNumber)) {
                    return ServerResponse.createByErrorCodeMessage(
                            MerchantRegisterUploadByApplet.FAILURE_TO_IDENTIFY.getCode(),
                            "识别不成功，请上传清晰结算银行卡正面",
                            myBankPhotoDto
                    );
                }
                myBankPhotoDto.setBankCardNumber(bankCardNumber);
                log.info("银行卡", myBankPhotoDto.getBankCardNumber());
            }
        } catch (Exception e) {
            return ServerResponse.createByErrorCodeMessage(
                    MerchantRegisterUploadByApplet.FAILURE_TO_IDENTIFY.getCode(),
                    e.getMessage(),
                    myBankPhotoDto
            );
        }
        /**
         * 上传成功后识别图片-end
         */
        return ServerResponse.createBySuccess(myBankPhotoDto);
    }

    /**
     * 商户进件-微信小程序端
     *
     * @param merchantDto
     * @param userInfo
     * @return
     */
    @Override
    public ServerResponse merchantRegisterByApplet(MerchantDto merchantDto, UserInfo userInfo) throws IOException, NoSuchAlgorithmException, NoSuchProviderException, KeyManagementException {
        log.info("merchantDto");
        log.info(JSON.toJSONString(merchantDto));

        ServerResponse serverResponse = this.checkParam(merchantDto);
        if (!serverResponse.getIsSuccess()) {
            return serverResponse;
        }

        // 判断商户订单号是否存
        String outTradeNo;
        if (StringUtils.isEmpty(merchantDto.getOutTradeNo())) {
            outTradeNo = UUID.randomUUID().toString();
            PayCompany payCompany = payCompanyService.findDefaultPayCompany(1);
            merchantDto.setPayCompanyCode(payCompany.getCode());
            int random = (int) (Math.random() * 900 + 100);
            String email = String.valueOf(System.currentTimeMillis()) + random + "@qq.com";
            merchantDto.setEmail(email);
        } else {
            outTradeNo = merchantDto.getOutTradeNo();
        }
        //组装进件参数
        MerchantBankCardDto merchantBankCard = new MerchantBankCardDto(
                merchantDto.getBankCardNo(),   //银行卡号
                merchantDto.getBankCertName(),  //账户名
                merchantDto.getAccountType(), //结算类型，01：对私 02：对公
                merchantDto.getContactLine(),//联行号
                merchantDto.getBankName(),//银行名称
                merchantDto.getBankProvince(),//开户行省
                merchantDto.getBankCity(),//开户行市
                PrincipalCertTypeEnum.IdentityCard.getCertCode(),
                merchantDto.getPrincipalCertNo(),//身份证号
                merchantDto.getBankRegion(),//持卡人地址
                merchantDto.getBankCardA(),//银行卡正面
                merchantDto.getBankCardB()//银行卡反面
        );
        List<MerchantFeeParamDto> feeParamList = new ArrayList<>();
        MerchantDetailDto merchantDetail = new MerchantDetailDto(
                merchantDto.getLegalPerson(),//企业法人名称 个体工商户不需要填写
                merchantDto.getBussAuthNum(),//营业执照号
                merchantDto.getPrincipalPerson(),//负责人名称或企业法人代表
                merchantDto.getContactMobile(),//负责人手机号
                PrincipalCertTypeEnum.IdentityCard.getCertCode(),
                merchantDto.getPrincipalCertNo(),//身份证号
                merchantDto.getProvinceCode(),//商户所在省
                merchantDto.getCityCode(),//市
                merchantDto.getDistrictCode(),//区
                merchantDto.getAddress(),//商户所在详细地址
                merchantDto.getEmail(),//邮箱
                merchantDto.getServicePhoneNo(),//公司电话
                "",
                "",
                merchantDto.getCertPhotoA(),//身份证正面
                merchantDto.getCertPhotoB(), // 身份证反面
                merchantDto.getLicensePhoto(),
                merchantDto.getIndustryLicensePhoto(),
                merchantDto.getShopPhoto(), //门头照
                merchantDto.getShopEntrancePhoto(), //场地内景照
                "",
                merchantDto.getCheckStandPhoto(),
                merchantDto.getHandHoldIdCard()
        );
        //费率
        feeParamList.add(new MerchantFeeParamDto(PayChannelEnum.WX.getChnCode(), MerchantFeeTypeEnum.T1.getFeeCode(), feeValue));
        feeParamList.add(new MerchantFeeParamDto(PayChannelEnum.Ali.getChnCode(), MerchantFeeTypeEnum.T1.getFeeCode(), feeValue));
        //outTradeNo 必须每次都一样 如果不一样那么提交过来就是修改或者报错
        // 修改的话需要满足 条件 商户状态是 平台审核以及等待提交这个状态才会修改
        merchantDto.setOutTradeNo(outTradeNo);
        if (MerchantTypeEnum.Natural.getCode().equals(merchantDto.getMerchantType())) {
            merchantDto.setMerchantName("商户_" + merchantDto.getPrincipalPerson());
        } else {
            merchantDto.setMerchantName(merchantDto.getLegalPerson());
        }
        merchantDto.setMccCode(MccEnum.Entertainment.getMccCode());
        merchantDto.setDealType(DealTypeEnum.EntityAndInternet.getDealCode());
        merchantDto.setStlTyp("1");
        int i = (int) (Math.random() * 900) + 100;
        String username = merchantDto.getContactMobile() + "/" + i;
        merchantDto.setUsername(username);
        merchantDto.setPath(configProperties.getClientBackEndUrl() + "/");
        log.info("merchantDto-2");
        log.info(JSON.toJSONString(merchantDto));
        JSONObject jsonObject = JSONObject.parseObject(JSON.toJSONString(merchantDto), Feature.OrderedField);
        jsonObject.put("merchantDetail", merchantDetail);
        jsonObject.put("merchantBankCard", merchantBankCard);
        jsonObject.put("merchantFeeList", feeParamList);
        final String uncommittedMerchantInfoKey = String.format(RedisKey.UNCOMMITTED_MERCHANT_INFO, userInfo.getId());
        rabbitSenderService.sendReplayMerchantSubmitRemoveInfoLazyQueue(uncommittedMerchantInfoKey, 5 * 1000);

        String param = HttpUtils.format(agencyConfig, jsonObject, FunctionEnum.MERCHANT_REGISTER, merchantDto.getPayCompanyCode());
        log.info("请求报文: {}", param);
        String response = HttpsMain.httpsReq(MiddlewareConfig.MerchantRegists, param);
        log.info("响应报文: {}", response);
        final Map<String, Object> result = HttpUtils.getResultData(response);
        log.info("响应报文result: {}", result);
        if (RequestStatus.SUCCESS.getCode().equals(result.get("status")) && RequestStatus.SUCCESS_CODE.getCode().equals(result.get("code"))) {
            Map<String, String> resMap = (Map<String, String>) result.get("data");
            Merchant merchant = new Merchant();
            merchant.setOutTradeNo(outTradeNo);
            MerchantVo merchantVo = merchantDao.findMerchantByOutTradeNo(merchant);
            if (StringUtils.isEmpty(merchantVo)) {
                // 添加资质编号
                Qualification qualification = new Qualification();
                qualification.setCertNo(resMap.get("certNo"));
                qualification.setUserId(userInfo.getId());
                qualification.setType(QualificationTypeEnum.MAIN_QUALIFICATIONS.getCode());
                if (MerchantTypeEnum.Natural.getCode().equals(merchantDto.getMerchantType())) {
                    qualification.setName(merchantDto.getPrincipalPerson());
                } else {
                    qualification.setName(merchantDto.getLegalPerson());
                }
                qualificationService.addQualification(qualification);
                // 添加商户
                merchant.setQualificationId(qualification.getId());
                merchant.setMerchantId(resMap.get("hlMerchantId"));
                merchant.setFeeValue(feeValue);
                merchant.setPayCompanyCode(merchantDto.getPayCompanyCode());
                merchant.setStatus(MerchantStatusEnum.AUDITING_YIHAO.getCode());
                merchant.setMerchantShortName(merchantDto.getMerchantShortName());
                merchantDao.addMerchant(merchant);
                MerchantPayCompany merchantPayCompany = new MerchantPayCompany();
                merchantPayCompany.setMchId(merchant.getId());
                merchantPayCompany.setPayCompanyCode(merchantDto.getPayCompanyCode());
                merchantPayCompany.setBankCardNo(merchantBankCard.getBankCardNo());
                merchantPayCompany.setBankCertName(merchantBankCard.getBankCertName());
                merchantPayCompanyService.addMerchantPayCompany(merchantPayCompany);
            } else {
                Qualification qualification = new Qualification();
                qualification.setCertNo(resMap.get("certNo"));
                if (MerchantTypeEnum.Natural.getCode().equals(merchantDto.getMerchantType())) {
                    qualification.setName(merchantDto.getPrincipalPerson());
                } else {
                    qualification.setName(merchantDto.getLegalPerson());
                }
                qualificationService.updateNameWhereCertNo(qualification);

                merchantDao.updateMerchant(merchant);
                MerchantPayCompanyDto merchantPayCompanyDto = new MerchantPayCompanyDto();
                merchantPayCompanyDto.setMchId(merchantVo.getId());
                merchantPayCompanyDto.setPayCompanyCode(merchantDto.getPayCompanyCode());
                merchantPayCompanyDto.setBankCardNo(merchantBankCard.getBankCardNo());
                merchantPayCompanyDto.setBankCertName(merchantBankCard.getBankCertName());
                merchantPayCompanyService.update(merchantPayCompanyDto);
            }
            UserDto userDto = new UserDto();
            userDto.setId(userInfo.getId());
            userDto.setReceiptType(MchTypeEnum.OWN.getCode());
            userService.updateUserReceiptType(userDto);
            return ServerResponse.createBySuccess(merchant);
        } else {
            return ServerResponse.createByErrorMessage((String) result.get("msg"));
        }
    }

    @Getter
    private enum MerchantRegisterByAppletError {
        PARAM_ERROR("10001", "参数有误"),
        ;

        private String code;
        private String desc;

        MerchantRegisterByAppletError(String code, String desc) {
            this.code = code;
            this.desc = desc;
        }
    }

    /**
     * 校验分账进件资料合法性
     */
    private ServerResponse checkParamSub(MerchantDto merchantDto) {
        if (StringUtils.isEmpty(merchantDto.getMerchantType())) {
            return ServerResponse.createByErrorCodeMessage(MerchantRegisterByAppletError.PARAM_ERROR.getCode(), "商户类型不能为空");
        }
        if (StringUtils.isEmpty(merchantDto.getAccountType())) {
            return ServerResponse.createByErrorCodeMessage(MerchantRegisterByAppletError.PARAM_ERROR.getCode(), "银行卡类型不能为空");
        }
        if (StringUtils.isEmpty(merchantDto.getCertPhotoA())) {
            return ServerResponse.createByErrorCodeMessage(MerchantRegisterByAppletError.PARAM_ERROR.getCode(), "身份证正面照片不能为空");
        }
        if (StringUtils.isEmpty(merchantDto.getCertPhotoB())) {
            return ServerResponse.createByErrorCodeMessage(MerchantRegisterByAppletError.PARAM_ERROR.getCode(), "身份证反面照片不能为空");
        }
        if (StringUtils.isEmpty(merchantDto.getPrincipalCertNo())) {
            return ServerResponse.createByErrorCodeMessage(MerchantRegisterByAppletError.PARAM_ERROR.getCode(), "身份证号码不能为空");
        }
        if (StringUtils.isEmpty(merchantDto.getPrincipalPerson())) {
            return ServerResponse.createByErrorCodeMessage(MerchantRegisterByAppletError.PARAM_ERROR.getCode(), "身份证姓名不能为空");
        }
        if (StringUtils.isEmpty(merchantDto.getContactMobile())) {
            return ServerResponse.createByErrorCodeMessage(MerchantRegisterByAppletError.PARAM_ERROR.getCode(), "手机号不能为空");
        }
        if (StringUtils.isEmpty(merchantDto.getServicePhoneNo())) {
            return ServerResponse.createByErrorCodeMessage(MerchantRegisterByAppletError.PARAM_ERROR.getCode(), "场地联系电话不能为空");
        }
        if (!MerchantTypeEnum.Enterprising.getCode().equals(merchantDto.getMerchantType()) && StringUtils.isEmpty(merchantDto.getBankCardA())) {
            return ServerResponse.createByErrorCodeMessage(MerchantRegisterByAppletError.PARAM_ERROR.getCode(), "银行卡正面不能为空");
        }
        if (!MerchantTypeEnum.Enterprising.getCode().equals(merchantDto.getMerchantType()) && StringUtils.isEmpty(merchantDto.getBankCardB())) {
            return ServerResponse.createByErrorCodeMessage(MerchantRegisterByAppletError.PARAM_ERROR.getCode(), "银行卡反面不能为空");
        }
        if (StringUtils.isEmpty(merchantDto.getBankCardNo())) {
            return ServerResponse.createByErrorCodeMessage(MerchantRegisterByAppletError.PARAM_ERROR.getCode(), "银行卡号不能为空");
        }
        if (StringUtils.isEmpty(merchantDto.getBankName())) {
            return ServerResponse.createByErrorCodeMessage(MerchantRegisterByAppletError.PARAM_ERROR.getCode(), "银行卡银行名称不能为空");
        }
        if (StringUtils.isEmpty(merchantDto.getBankProvince())) {
            return ServerResponse.createByErrorCodeMessage(MerchantRegisterByAppletError.PARAM_ERROR.getCode(), "银行卡开户地区-省 不能为空");
        }
        if (StringUtils.isEmpty(merchantDto.getBankCity())) {
            return ServerResponse.createByErrorCodeMessage(MerchantRegisterByAppletError.PARAM_ERROR.getCode(), "银行卡开户地区-市 不能为空");
        }
        if (StringUtils.isEmpty(merchantDto.getContactLine())) {
            return ServerResponse.createByErrorCodeMessage(MerchantRegisterByAppletError.PARAM_ERROR.getCode(), "联行号不能为空");
        }
        if (!MerchantTypeEnum.Natural.getCode().equals(merchantDto.getMerchantType()) && StringUtils.isEmpty(merchantDto.getLicensePhoto())) {
            return ServerResponse.createByErrorCodeMessage(MerchantRegisterByAppletError.PARAM_ERROR.getCode(), "营业执照照片不能为空");
        }
        if (!MerchantTypeEnum.Natural.getCode().equals(merchantDto.getMerchantType()) && StringUtils.isEmpty(merchantDto.getLegalPerson())) {
            return ServerResponse.createByErrorCodeMessage(MerchantRegisterByAppletError.PARAM_ERROR.getCode(), "营业执照名称不能为空");
        }
        if (!MerchantTypeEnum.Natural.getCode().equals(merchantDto.getMerchantType()) && StringUtils.isEmpty(merchantDto.getBussAuthNum())) {
            return ServerResponse.createByErrorCodeMessage(MerchantRegisterByAppletError.PARAM_ERROR.getCode(), "统一社会信用代码不能为空");
        }

//        if (StringUtils.isEmpty(merchantDto.getHandHoldIdCard())) {
//            return ServerResponse.createByErrorCodeMessage(MerchantRegisterByAppletError.PARAM_ERROR.getCode(), "手持身份证照不能为空");
//        }
        return ServerResponse.createBySuccess();
    }

    /**
     * 校验进件资料合法性
     *
     * @param merchantDto
     */
    private ServerResponse checkParam(MerchantDto merchantDto) {
        if (StringUtils.isEmpty(merchantDto.getMerchantType())) {
            return ServerResponse.createByErrorCodeMessage(MerchantRegisterByAppletError.PARAM_ERROR.getCode(), "商户类型不能为空");
        }
        if (StringUtils.isEmpty(merchantDto.getAccountType())) {
            return ServerResponse.createByErrorCodeMessage(MerchantRegisterByAppletError.PARAM_ERROR.getCode(), "银行卡类型不能为空");
        }
        if (StringUtils.isEmpty(merchantDto.getCertPhotoA())) {
            return ServerResponse.createByErrorCodeMessage(MerchantRegisterByAppletError.PARAM_ERROR.getCode(), "身份证正面照片不能为空");
        }
        if (StringUtils.isEmpty(merchantDto.getCertPhotoB())) {
            return ServerResponse.createByErrorCodeMessage(MerchantRegisterByAppletError.PARAM_ERROR.getCode(), "身份证反面照片不能为空");
        }
        if (StringUtils.isEmpty(merchantDto.getPrincipalCertNo())) {
            return ServerResponse.createByErrorCodeMessage(MerchantRegisterByAppletError.PARAM_ERROR.getCode(), "身份证号码不能为空");
        }
        if (StringUtils.isEmpty(merchantDto.getPrincipalPerson())) {
            return ServerResponse.createByErrorCodeMessage(MerchantRegisterByAppletError.PARAM_ERROR.getCode(), "身份证姓名不能为空");
        }
        if (StringUtils.isEmpty(merchantDto.getContactMobile())) {
            return ServerResponse.createByErrorCodeMessage(MerchantRegisterByAppletError.PARAM_ERROR.getCode(), "手机号不能为空");
        }
        if (StringUtils.isEmpty(merchantDto.getServicePhoneNo())) {
            return ServerResponse.createByErrorCodeMessage(MerchantRegisterByAppletError.PARAM_ERROR.getCode(), "场地联系电话不能为空");
        }
        if (!MerchantTypeEnum.Enterprising.getCode().equals(merchantDto.getMerchantType()) && StringUtils.isEmpty(merchantDto.getBankCardA())) {
            return ServerResponse.createByErrorCodeMessage(MerchantRegisterByAppletError.PARAM_ERROR.getCode(), "银行卡正面不能为空");
        }
        if (!MerchantTypeEnum.Enterprising.getCode().equals(merchantDto.getMerchantType()) && StringUtils.isEmpty(merchantDto.getBankCardB())) {
            return ServerResponse.createByErrorCodeMessage(MerchantRegisterByAppletError.PARAM_ERROR.getCode(), "银行卡反面不能为空");
        }
        if (StringUtils.isEmpty(merchantDto.getBankCardNo())) {
            return ServerResponse.createByErrorCodeMessage(MerchantRegisterByAppletError.PARAM_ERROR.getCode(), "银行卡号不能为空");
        }
        if (StringUtils.isEmpty(merchantDto.getBankName())) {
            return ServerResponse.createByErrorCodeMessage(MerchantRegisterByAppletError.PARAM_ERROR.getCode(), "银行卡银行名称不能为空");
        }
        if (StringUtils.isEmpty(merchantDto.getBankProvince())) {
            return ServerResponse.createByErrorCodeMessage(MerchantRegisterByAppletError.PARAM_ERROR.getCode(), "银行卡开户地区-省 不能为空");
        }
        if (StringUtils.isEmpty(merchantDto.getBankCity())) {
            return ServerResponse.createByErrorCodeMessage(MerchantRegisterByAppletError.PARAM_ERROR.getCode(), "银行卡开户地区-市 不能为空");
        }
        if (StringUtils.isEmpty(merchantDto.getContactLine())) {
            return ServerResponse.createByErrorCodeMessage(MerchantRegisterByAppletError.PARAM_ERROR.getCode(), "联行号不能为空");
        }
        if (!MerchantTypeEnum.Natural.getCode().equals(merchantDto.getMerchantType()) && StringUtils.isEmpty(merchantDto.getLicensePhoto())) {
            return ServerResponse.createByErrorCodeMessage(MerchantRegisterByAppletError.PARAM_ERROR.getCode(), "营业执照照片不能为空");
        }
        if (MerchantTypeEnum.Enterprising.getCode().equals(merchantDto.getMerchantType()) && StringUtils.isEmpty(merchantDto.getIndustryLicensePhoto())) {
            return ServerResponse.createByErrorCodeMessage(MerchantRegisterByAppletError.PARAM_ERROR.getCode(), "开户许可证照片不能为空");
        }
        if (!MerchantTypeEnum.Natural.getCode().equals(merchantDto.getMerchantType()) && StringUtils.isEmpty(merchantDto.getLegalPerson())) {
            return ServerResponse.createByErrorCodeMessage(MerchantRegisterByAppletError.PARAM_ERROR.getCode(), "营业执照名称不能为空");
        }
        if (!MerchantTypeEnum.Natural.getCode().equals(merchantDto.getMerchantType()) && StringUtils.isEmpty(merchantDto.getBussAuthNum())) {
            return ServerResponse.createByErrorCodeMessage(MerchantRegisterByAppletError.PARAM_ERROR.getCode(), "统一社会信用代码不能为空");
        }
        if (StringUtils.isEmpty(merchantDto.getProvinceCode())) {
            return ServerResponse.createByErrorCodeMessage(MerchantRegisterByAppletError.PARAM_ERROR.getCode(), "营业地区-省 不能为空");
        }
        if (StringUtils.isEmpty(merchantDto.getCityCode())) {
            return ServerResponse.createByErrorCodeMessage(MerchantRegisterByAppletError.PARAM_ERROR.getCode(), "营业地区-市 不能为空");
        }
        if (StringUtils.isEmpty(merchantDto.getDistrictCode())) {
            return ServerResponse.createByErrorCodeMessage(MerchantRegisterByAppletError.PARAM_ERROR.getCode(), "营业地区-区 不能为空");
        }
        if (StringUtils.isEmpty(merchantDto.getAddress())) {
            return ServerResponse.createByErrorCodeMessage(MerchantRegisterByAppletError.PARAM_ERROR.getCode(), "详细地址不能为空");
        }
        if (StringUtils.isEmpty(merchantDto.getMerchantShortName())) {
            return ServerResponse.createByErrorCodeMessage(MerchantRegisterByAppletError.PARAM_ERROR.getCode(), "商户收款简称不能为空");
        }
        if (StringUtils.isEmpty(merchantDto.getShopPhoto())) {
            return ServerResponse.createByErrorCodeMessage(MerchantRegisterByAppletError.PARAM_ERROR.getCode(), "门头照不能为空");
        }
        if (StringUtils.isEmpty(merchantDto.getShopEntrancePhoto())) {
            return ServerResponse.createByErrorCodeMessage(MerchantRegisterByAppletError.PARAM_ERROR.getCode(), "内景照不能为空");
        }
        if (StringUtils.isEmpty(merchantDto.getCheckStandPhoto())) {
            return ServerResponse.createByErrorCodeMessage(MerchantRegisterByAppletError.PARAM_ERROR.getCode(), "收银台照不能为空");
        }
//        if (StringUtils.isEmpty(merchantDto.getHandHoldIdCard())) {
//            return ServerResponse.createByErrorCodeMessage(MerchantRegisterByAppletError.PARAM_ERROR.getCode(), "手持身份证照不能为空");
//        }
        // 判断个人商户简称不能包含“酒店”、“网吧”、“ktv”文字
        if (MerchantTypeEnum.Natural.getCode().equals(merchantDto.getMerchantType())) {
            try {
                // 如果有大写的英文就转成小写的英文,toLowerCase
                String name = merchantDto.getMerchantShortName().toLowerCase();
                if (name.contains("酒店") || name.contains("网吧") || name.contains("ktv")) {
                    return ServerResponse.createByErrorCodeMessage(MerchantRegisterByAppletError.PARAM_ERROR.getCode(), "个人商户简称不能包含“酒店”、“网吧”、“ktv”文字");
                }
            } catch (Exception e) {
                log.error("个人商户简称判断“酒店”、“网吧”、“ktv”异常");
                e.printStackTrace();
            }
        }
        return ServerResponse.createBySuccess();
    }

    /**
     * 0：未知错误
     * 10001：上传失败
     * 10002：识别失败
     */
    @Getter
    private enum MerchantRegisterUploadByApplet {
        DEFAULT_ERR("1", "未知错误"),
        UPLOAD_FAIL("10001", "上传失败"),
        FAILURE_TO_IDENTIFY("10002", "识别失败"),
        ;

        private String code;
        private String desc;


        MerchantRegisterUploadByApplet(String code, String desc) {
            this.code = code;
            this.desc = desc;
        }
    }
}
